apidog-reporter-allure
Version:
An adapter for apidog proving reports in allure format
216 lines (215 loc) • 7.8 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.handleHttpExecution = handleHttpExecution;
var _allureJsCommons = require("allure-js-commons");
var _allure = _interopRequireDefault(require("../allure"));
var _utils = require("../utils");
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
const contentTypes = {
json: _allureJsCommons.ContentType.JSON,
html: _allureJsCommons.ContentType.HTML,
xml: _allureJsCommons.ContentType.XML,
raw: _allureJsCommons.ContentType.TEXT
};
function contentTypeOf(headers) {
return headers?.find(({
key
}) => key.toLowerCase() === 'content-type')?.value;
}
function formatBody(headers, body) {
if (!body.length) {
return '';
}
return (0, _utils.prettyBody)(body, contentTypeOf(headers));
}
function attachBody(name, headers, body) {
const formatted = formatBody(headers, body);
if (!formatted.length) {
return;
}
_allure.default.attach(name, formatted, contentTypes[(0, _utils.parseContentType)(contentTypeOf(headers))]);
}
function responseBody({
response
}) {
if (!response?.stream?.data?.length) {
return '';
}
const content = new TextDecoder().decode(new Uint8Array(response.stream.data));
return formatBody(response.headers || [], content);
}
function withBody(trace, body) {
return body.length ? `${trace}\n\nResponse body:\n${body}` : trace;
}
function resolveUrl(req) {
const variables = {};
if (req.url.variable) {
req.url.variable.forEach(v => {
variables[v.key] = v.value;
});
}
const path = (req.url.path || []).map(segment => segment.replace(/\{\{([^}]+)\}\}/g, (_, key) => variables[key] ?? `{{${key}}}`)).join('/');
const base = req.baseUrl.replace(/\/$/, '');
let url = path ? `${base}/${path}` : base;
const query = req.url.query;
if (query && query.length > 0) {
const qs = query.filter(q => q.key).map(q => `${encodeURIComponent(q.key)}=${encodeURIComponent(q.value ?? '')}`).join('&');
if (qs) url += `?${qs}`;
}
return url;
}
function handleHttpRequest(item, step) {
const {
requestError,
metaInfo,
timings,
request: req,
response,
responseValidation,
scriptErrors
} = item;
const body = responseBody(item);
const resolvedUrl = req ? resolveUrl(req) : undefined;
step.addParameter('name', metaInfo.httpApiName);
if (resolvedUrl) {
step.addParameter('url', resolvedUrl);
}
_allure.default.startStep(`${metaInfo.httpApiMethod} ${metaInfo.httpApiPath}`, timings.preProcessorsCompleted);
if (req) {
_allure.default.startStep('Request', timings.preProcessorsCompleted);
if (req.body && req.body.raw) {
attachBody('Request body', req.headers, req.body.raw);
}
_allure.default.stepStatus({
status: _allureJsCommons.Status.PASSED,
message: `URL: ${resolvedUrl}\n\nHeaders:\n${(0, _utils.prettyHeaders)(req.headers)}`,
end: timings.preProcessorsCompleted
});
if (requestError) {
_allure.default.stepStatus({
status: _allureJsCommons.Status.FAILED,
message: `Response code: '${requestError.code}'\nReason: '${requestError.message}'`
});
_allure.default.testStatus({
message: `[HTTP] ${metaInfo.httpApiMethod} ${metaInfo.httpApiPath}`,
trace: `Response code: '${requestError.code}'\nReason: '${requestError.message}`
});
} else if (response) {
_allure.default.attach('Response body', body, contentTypes[(0, _utils.parseContentType)(contentTypeOf(response.headers))]);
_allure.default.stepStatus({
message: `Status code: ${response.code}\n\n${response.cookies?.length > 0 ? `Cookies:\n\n${(0, _utils.prettyHeaders)(response.cookies)}\n\n` : ''}Headers:\n${response.headers ? (0, _utils.prettyHeaders)(response.headers) : '[]'}`
});
}
if (responseValidation) {
let isCorrect = true;
if (responseValidation.schema) {
_allure.default.startStep(`Validate schema`, timings.postProcessorsStarted);
if (!responseValidation.schema.valid) {
isCorrect = false;
_allure.default.stepStatus({
status: _allureJsCommons.Status.FAILED,
message: withBody(responseValidation.schema.message, body),
end: timings.postProcessorsStarted
});
_allure.default.testStatus({
message: `[HTTP] ${metaInfo.httpApiMethod} ${metaInfo.httpApiPath}`,
trace: withBody(`${response ? `Response code: '${response.code}'\n\n` : ''}Schema was invalid: ${responseValidation.schema.message}`, body)
});
} else {
_allure.default.stepStatus({
status: _allureJsCommons.Status.PASSED,
end: timings.postProcessorsStarted
});
}
}
if (responseValidation.responseCode) {
_allure.default.startStep(`Validate response code`, timings.postProcessorsStarted);
if (!responseValidation.responseCode.valid) {
isCorrect = false;
_allure.default.stepStatus({
status: _allureJsCommons.Status.FAILED,
message: withBody(responseValidation.responseCode.message, body),
end: timings.postProcessorsStarted
});
_allure.default.testStatus({
message: `[HTTP] ${metaInfo.httpApiMethod} ${metaInfo.httpApiPath}`,
trace: withBody(responseValidation.responseCode.message, body)
});
} else {
_allure.default.stepStatus({
status: _allureJsCommons.Status.PASSED,
end: timings.postProcessorsStarted
});
}
}
_allure.default.stepStatus({
status: isCorrect ? _allureJsCommons.Status.PASSED : _allureJsCommons.Status.FAILED
});
}
if (scriptErrors && scriptErrors.length > 0) {
scriptErrors.map(({
error
}) => error).sort((a1, a2) => a1.timestamp - a2.timestamp).forEach(({
message,
timestamp
}) => {
_allure.default.testStatus({
message
});
_allure.default.startStep(message, timestamp);
_allure.default.stepStatus({
status: _allureJsCommons.Status.FAILED,
end: timestamp
});
});
}
}
_allure.default.endStep(timings.postProcessorsStarted);
}
function handleHttpAssertions(item, time) {
const {
assertions
} = item;
if (!assertions) {
return;
}
const body = responseBody(item);
_allure.default.startStep('Assertions', time);
let isSuccess = true;
assertions.forEach(assertion => {
isSuccess &&= assertion.passed;
_allure.default.startStep(assertion.name, time);
if (!assertion.passed) {
_allure.default.stepStatus({
status: _allureJsCommons.Status.FAILED,
message: withBody(JSON.stringify(assertion.error), body),
end: time
});
_allure.default.testStatus({
message: assertion.name,
trace: withBody(JSON.stringify(assertion.error), body)
});
} else {
_allure.default.stepStatus({
status: _allureJsCommons.Status.PASSED,
end: time
});
}
});
_allure.default.stepStatus({
status: isSuccess ? _allureJsCommons.Status.PASSED : _allureJsCommons.Status.FAILED,
end: time
});
}
function handleHttpExecution(item) {
_allure.default.startStep(`[${item.metaInfo.type}] ${item.name}`, item.timings.started);
if (_allure.default.currentStep) {
_allure.default.currentStep.step.status = item.passed ? _allureJsCommons.Status.PASSED : _allureJsCommons.Status.FAILED;
handleHttpRequest(item, _allure.default.currentStep.step);
handleHttpAssertions(item, item.timings.postProcessorsStarted);
_allure.default.endStep(item.timings.completed);
}
return item.passed;
}