Connect Bitbucket Pipelines to TestCollab with @testcollab/cli. The pipeline creates
a TestCollab plan from CI-tagged cases, runs your tests, and uploads their JUnit XML results
before returning the real test status to Bitbucket.
The default workflow is createTestPlan → tests → report. It
does not require createBuild or gate.
For CLI installation and other reporting modes, see TestCollab CLI: Install and First Run.
Prerequisites
- A TestCollab project containing the automated cases.
- A CI tag applied to those cases, plus the project ID, tag ID, and assignee user ID.
- A TestCollab API token belonging to the assignee. The user must be able to create and assign test plans.
- Bitbucket Pipelines enabled for the repository.
-
A reporter that writes JUnit XML. The complete example uses Jest and
jest-junit.
Install the reporter as a development dependency if needed:
npm install --save-dev jest-junit
Add Bitbucket repository variables
Open Repository settings > Pipelines > Repository variables and add:
| Variable | Value | Secured? |
|---|---|---|
TESTCOLLAB_TOKEN |
Your TestCollab API token | Yes |
TC_PROJECT_ID |
TestCollab project ID | No |
TC_CI_TAG_ID |
Tag ID selecting the CI cases | No |
TC_ASSIGNEE_ID |
User ID that owns the executions | No |
TC_API_URL |
https://api.testcollab.io |
No |
Create the token through Getting an API Token generated. Mark it as secured so Bitbucket masks its value in logs.
Complete bitbucket-pipelines.yml
The example keeps plan creation, test execution, and result upload in one step, so
tmp/tc_test_plan and the JUnit file remain available. The shell captures the test
failure, uploads the report, and then restores the correct exit status.
image: node:22-bookworm
pipelines:
default:
- step:
name: Test and report to TestCollab
caches:
- node
script:
- npm ci
- |
set -e
npx @testcollab/cli createTestPlan \
--project "$TC_PROJECT_ID" \
--ci-tag-id "$TC_CI_TAG_ID" \
--assignee-id "$TC_ASSIGNEE_ID" \
--api-url "$TC_API_URL"
. tmp/tc_test_plan
mkdir -p test-results
set +e
JEST_JUNIT_OUTPUT_DIR=./test-results \
JEST_JUNIT_OUTPUT_NAME=results.xml \
npm test -- --ci --reporters=default --reporters=jest-junit
TEST_EXIT=$?
npx @testcollab/cli report \
--project "$TC_PROJECT_ID" \
--test-plan-id "$TESTCOLLAB_TEST_PLAN_ID" \
--format junit \
--result-file ./test-results/results.xml \
--api-url "$TC_API_URL"
REPORT_EXIT=$?
set -e
if [ "$REPORT_EXIT" -ne 0 ]; then
exit "$REPORT_EXIT"
fi
exit "$TEST_EXIT"
artifacts:
- test-results/**
To run only on selected branches, move the same step under
pipelines: branches: main: or another Bitbucket branch pattern. Do not duplicate the
TestCollab token in the YAML.
How the Bitbucket pipeline works
-
createTestPlancreates a plan from the CI-tagged cases and writes its ID totmp/tc_test_plan. -
The POSIX
.command loadsTESTCOLLAB_TEST_PLAN_IDinto the same shell. -
Jest writes
test-results/results.xml, and the script saves Jest's exit status. tc reportuploads the JUnit results to their TestCollab executions.- The script returns a reporting failure first, otherwise the original test status. Failed tests remain a failed Bitbucket step.
- The XML is retained as a Bitbucket artifact for later inspection.
Map JUnit results with [TC-42]
Put an explicit TestCollab case ID in each automated test title. The CLI recognizes
[TC-42], TC-42, id-42, and testcase-42,
case-insensitively.
test('[TC-42] customer can sign in', async () => {
// Test steps and assertions
});
The case must carry the selected CI tag and appear in the created plan. The number is the TestCollab test case ID, not a Bitbucket issue number.
Use Playwright, pytest, or Maven
Keep the plan and report commands, but replace Jest with the JUnit command for your runner:
# Playwright
PLAYWRIGHT_JUNIT_OUTPUT_NAME=test-results/results.xml \
npx playwright test --reporter=junit
# pytest
pytest --junitxml=test-results/results.xml
# Maven Surefire
mvn test
Choose an image that contains the required runtime. For a non-Node image, Node.js 18 or newer must
also be available for @testcollab/cli. Update --result-file to the
actual XML path, and merge multiple JUnit files before upload.
Optional build traceability and quality gates
tc createBuild recognizes Bitbucket Pipelines. When its flags are omitted, the CLI
can read the build number, commit SHA, repository URL, commit URL, and pipeline URL from
Bitbucket's predefined environment variables. Add that command only when you also want to record
the deployed build and link a plan to its version.
After tc report, you can independently add
a quality gate
when a deployment must wait for defined result criteria. See
Creating Builds from Your CI/CD Pipeline
for optional build traceability. Neither extension is required, and you can use either one without
the other.
Use the EU region
Set the repository variable TC_API_URL to this value for an EU account:
https://api-eu.testcollab.io
The pipeline already passes the variable to both CLI commands.
Troubleshooting
No API key provided
Confirm TESTCOLLAB_TOKEN exists as a secured repository or deployment variable and is
available to this pipeline context.
The test-results artifact is empty
Confirm jest-junit is installed and writes test-results/results.xml. Use
the same path in the reporter, tc report, and artifact declaration.
The TestCollab cases remain unexecuted
Inspect each JUnit <testcase name> for [TC-42]. Confirm the case
is selected by the CI tag and assigned to the API token owner.
Failed tests do not fail the step
Do not finish the script with || true. Preserve TEST_EXIT and return it
after tc report succeeds.


