cd6ff8830c
CI Feature / Load example-gitea-env.conf to pipeline env (push) Successful in 27s
acc-tests Cucumber test report
CI Feature / Cucumber tests (push) Failing after 51s
unit-tests Bats test report
CI Feature / Bats tests (push) Failing after 1m32s
CI Feature / Report Summary (push) Successful in 5s
121 lines
4.4 KiB
JavaScript
121 lines
4.4 KiB
JavaScript
const { execSync, spawn } = require('child_process');
|
|
const { When, Then, Given } = require('@cucumber/cucumber');
|
|
const fs = require('fs');
|
|
const path = require('path');
|
|
const os = require('os');
|
|
|
|
const PROJECT_ROOT = path.resolve(__dirname, '..', '..', '..');
|
|
const MOCK_SERVER = path.join(PROJECT_ROOT, 'tests', 'helpers', 'mock-server.py');
|
|
const DISPATCH_SCRIPT = path.join(PROJECT_ROOT, 'scripts', 'dispatch-workflow.sh');
|
|
|
|
function bash(cmd) {
|
|
try {
|
|
const out = execSync(`bash -c ${JSON.stringify(cmd)}`, {
|
|
cwd: PROJECT_ROOT,
|
|
encoding: 'utf-8',
|
|
stdio: ['pipe', 'pipe', 'pipe'],
|
|
});
|
|
return { status: 0, stdout: out };
|
|
} catch (e) {
|
|
return { status: e.status, stdout: e.stdout || '', stderr: e.stderr || '' };
|
|
}
|
|
}
|
|
|
|
function getFreePort() {
|
|
const out = execSync(`python3 -c "import socket; s=socket.socket(); s.bind(('',0)); print(s.getsockname()[1]); s.close()"`, { encoding: 'utf-8' });
|
|
return parseInt(out.trim(), 10);
|
|
}
|
|
|
|
function setupMock(seqJson) {
|
|
const port = getFreePort();
|
|
process.env.MOCK_PORT = String(port);
|
|
process.env.GITEA_API_URL = `http://localhost:${port}`;
|
|
|
|
const seqFile = path.join(os.tmpdir(), `cucumber_seq_${Date.now()}.json`);
|
|
fs.writeFileSync(seqFile, seqJson);
|
|
const idxFile = `${seqFile}.idx`;
|
|
fs.writeFileSync(idxFile, '0');
|
|
|
|
const reqFile = path.join(os.tmpdir(), `cucumber_req_${Date.now()}.log`);
|
|
const configFile = path.join(os.tmpdir(), `cucumber_cfg_${Date.now()}.txt`);
|
|
fs.writeFileSync(configFile, `SEQUENCE\n${seqJson}\n${idxFile}`);
|
|
|
|
const proc = spawn('python3', [MOCK_SERVER, String(port), configFile, reqFile], {
|
|
cwd: PROJECT_ROOT,
|
|
detached: true,
|
|
stdio: 'ignore',
|
|
});
|
|
proc.unref();
|
|
|
|
for (let i = 0; i < 20; i++) {
|
|
try {
|
|
execSync(`nc -z localhost ${port}`, { stdio: 'ignore' });
|
|
fs.writeFileSync(idxFile, '0');
|
|
return;
|
|
} catch (_) {}
|
|
execSync('sleep 0.1', { stdio: 'ignore' });
|
|
}
|
|
throw new Error('Mock failed to start');
|
|
}
|
|
|
|
function runDispatch(args) {
|
|
return bash(`export DISPATCH_POLL_INTERVAL="0.1"; bash "${DISPATCH_SCRIPT}" ${args}`);
|
|
}
|
|
|
|
Given('a deployment has completed in the target environment', function () {
|
|
});
|
|
|
|
Given('the test project repository exists with test definitions', function () {
|
|
});
|
|
|
|
When('a test workflow is dispatched to a test project', function () {
|
|
setupMock(JSON.stringify([
|
|
{ code: 201 },
|
|
{ code: 200, body: { workflow_runs: [{ id: 1, status: 'running' }] } },
|
|
{ code: 200, body: { id: 1, status: 'completed', conclusion: 'success' } },
|
|
]));
|
|
const url = process.env.GITEA_API_URL;
|
|
const r = runDispatch(`"test-owner/test-repo" "test.yml" "main" '{"version":"1.2.3"}' "${url}" "test-token-abc123"`);
|
|
this.dispatchResult = r.status;
|
|
});
|
|
|
|
Then('the pipeline waits until the test workflow finishes', function () {
|
|
if (this.dispatchResult !== 0) throw new Error(`Expected 0, got ${this.dispatchResult}`);
|
|
});
|
|
|
|
Then('the pipeline continues only after receiving a success result', function () {
|
|
if (this.dispatchResult !== 0) throw new Error('Expected pipeline to continue after success');
|
|
});
|
|
|
|
When('a test workflow is dispatched and the tests fail', function () {
|
|
setupMock(JSON.stringify([
|
|
{ code: 201 },
|
|
{ code: 200, body: { workflow_runs: [{ id: 1, status: 'running' }] } },
|
|
{ code: 200, body: { id: 1, status: 'completed', conclusion: 'failure' } },
|
|
]));
|
|
const url = process.env.GITEA_API_URL;
|
|
const r = runDispatch(`"test-owner/test-repo" "test.yml" "main" '{"version":"1.2.3"}' "${url}" "test-token-abc123"`);
|
|
this.dispatchResult = r.status;
|
|
});
|
|
|
|
Then('the calling pipeline reports failure', function () {
|
|
if (this.dispatchResult !== 1) throw new Error(`Expected failure exit 1, got ${this.dispatchResult}`);
|
|
});
|
|
|
|
When('a test workflow is dispatched but does not finish within the allowed time', function () {
|
|
setupMock(JSON.stringify([
|
|
{ code: 201 },
|
|
{ code: 200, body: { workflow_runs: [{ id: 1, status: 'running' }] } },
|
|
{ code: 200, body: { id: 1, status: 'running' } },
|
|
{ code: 200, body: { id: 1, status: 'running' } },
|
|
{ code: 200, body: { id: 1, status: 'running' } },
|
|
]));
|
|
const url = process.env.GITEA_API_URL;
|
|
const r = runDispatch(`"test-owner/test-repo" "test.yml" "main" '{"version":"1.2.3"}' "${url}" "test-token-abc123" "0.001"`);
|
|
this.dispatchResult = r.status;
|
|
});
|
|
|
|
Then('the calling pipeline reports a timeout error', function () {
|
|
if (this.dispatchResult !== 124) throw new Error(`Expected timeout exit 124, got ${this.dispatchResult}`);
|
|
});
|