Skip to content
Join Now Login

GitLab CI

GitLab CI/CD makes it easy to run tests on every push. With Gaffer, you can automatically upload and share test reports from your pipelines.

1. Add your upload token as a CI/CD variable

Section titled “1. Add your upload token as a CI/CD variable”
  1. Go to your GitLab project
  2. Navigate to SettingsCI/CDVariables
  3. Click Add variable
  4. Key: GAFFER_UPLOAD_TOKEN
  5. Value: Your Gaffer project upload token
  6. Check Mask variable to hide it in logs
test:
stage: test
script:
- npm ci
- npm test
after_script:
- |
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@test-results/junit.xml" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$CI_COMMIT_REF_NAME"'"}'
artifacts:
when: always
reports:
junit: test-results/junit.xml

GitLab CI provides these variables for your pipeline:

VariableDescriptionExample
$CI_COMMIT_SHAFull commit SHAabc123def456...
$CI_COMMIT_REF_NAMEBranch or tag namemain, feature/login
$CI_MERGE_REQUEST_SOURCE_BRANCH_NAMESource branch in MR pipelinesfeature/login
$CI_PROJECT_NAMEProject namemy-app
playwright:
stage: test
image: mcr.microsoft.com/playwright:v1.40.0-jammy
script:
- npm ci
- npx playwright install --with-deps
- npx playwright test
after_script:
- |
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@playwright-report/index.html" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$CI_COMMIT_REF_NAME"'","test_framework":"playwright","test_suite":"e2e"}'
artifacts:
when: always
paths:
- playwright-report/
jest:
stage: test
script:
- npm ci
- npm test -- --reporters=default --reporters=jest-junit
after_script:
- |
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@junit.xml" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$CI_COMMIT_REF_NAME"'","test_framework":"jest"}'
artifacts:
when: always
reports:
junit: junit.xml
pytest:
stage: test
image: python:3.11
script:
- pip install pytest pytest-html
- pytest --html=report.html --self-contained-html
after_script:
- |
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@report.html" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$CI_COMMIT_REF_NAME"'","test_framework":"pytest"}'
artifacts:
when: always
paths:
- report.html

For a standardized format across all your test frameworks, consider using CTRF:

test:
script:
- npm ci
# Install the CTRF reporter for your framework:
# npm install --save-dev jest-ctrf-json-reporter
# npm install --save-dev playwright-ctrf-json-reporter
# npm install --save-dev vitest-ctrf-json-reporter
- npm test -- --reporter=jest-ctrf-json-reporter
after_script:
- |
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@ctrf-report.json" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$CI_COMMIT_REF_NAME"'"}'

For merge request pipelines, use the source branch name:

test:
rules:
- if: $CI_MERGE_REQUEST_IID
script:
- npm test
after_script:
- |
BRANCH="${CI_MERGE_REQUEST_SOURCE_BRANCH_NAME:-$CI_COMMIT_REF_NAME}"
curl -X POST https://app.gaffer.sh/api/upload \
-H "X-API-Key: $GAFFER_UPLOAD_TOKEN" \
-F "files=@test-results/junit.xml" \
-F 'tags={"commitSha":"'"$CI_COMMIT_SHA"'","branch":"'"$BRANCH"'"}'
  • Verify GAFFER_UPLOAD_TOKEN is set in CI/CD variables
  • Check the variable is not marked “Protected” if running on unprotected branches
  • Ensure after_script is used (runs even when tests fail)
  • Check your upload token starts with gfr_
  • Verify the token is correctly copied (no extra spaces)

For merge request pipelines, use CI_MERGE_REQUEST_SOURCE_BRANCH_NAME instead of CI_COMMIT_REF_NAME.

Other CI Providers: GitHub Actions · CircleCI · Jenkins · Bitbucket · Azure DevOps