ci: harden typhon telemetry publisher quoting
This commit is contained in:
parent
5aa0b92de4
commit
bcdecee1a9
36
Jenkinsfile
vendored
36
Jenkinsfile
vendored
@ -107,8 +107,12 @@ function unescapeXml(value) {
|
||||
}
|
||||
|
||||
function attr(attrs, name) {
|
||||
const match = attrs.match(new RegExp(`(?:^|\\s)${name}="([^"]*)"`));
|
||||
return match ? unescapeXml(match[1]) : '';
|
||||
const needle = `${name}="`;
|
||||
const start = attrs.indexOf(needle);
|
||||
if (start < 0) return '';
|
||||
const valueStart = start + needle.length;
|
||||
const valueEnd = attrs.indexOf('"', valueStart);
|
||||
return valueEnd < 0 ? '' : unescapeXml(attrs.slice(valueStart, valueEnd));
|
||||
}
|
||||
|
||||
function collectSourceFiles(rootDir) {
|
||||
@ -134,7 +138,7 @@ function collectSourceFiles(rootDir) {
|
||||
}
|
||||
|
||||
function categoryForClassname(classname) {
|
||||
const normalized = String(classname || '').split('\\').join('/');
|
||||
const normalized = String(classname || '').split(String.fromCharCode(92)).join('/');
|
||||
const relative = normalized.includes('/tests/')
|
||||
? normalized.slice(normalized.indexOf('/tests/') + '/tests/'.length)
|
||||
: (normalized.startsWith('tests/') ? normalized.slice('tests/'.length) : normalized);
|
||||
@ -147,7 +151,7 @@ function categoryForClassname(classname) {
|
||||
|
||||
function parseTestCases(junit) {
|
||||
const cases = [];
|
||||
const re = new RegExp('<testcase\\b([^>]*)>([\\s\\S]*?)</testcase>|<testcase\\b([^>]*)/>', 'g');
|
||||
const re = new RegExp('<testcase([^>]*)>(.*?)</testcase>|<testcase([^>]*)/>', 'gs');
|
||||
let match;
|
||||
while ((match = re.exec(junit)) !== null) {
|
||||
const attrs = match[1] || match[3] || '';
|
||||
@ -174,7 +178,7 @@ const cov = fs.existsSync(coveragePath) ? JSON.parse(fs.readFileSync(coveragePat
|
||||
const total = cov.total || {};
|
||||
const sourceFiles = sourceRoots.flatMap((root) => collectSourceFiles(root));
|
||||
const overLimitFiles = sourceFiles
|
||||
.map((file) => ({ file, lines: fs.readFileSync(file, 'utf8').split(new RegExp('\\r?\\n')).length }))
|
||||
.map((file) => ({ file, lines: fs.readFileSync(file, 'utf8').split(String.fromCharCode(10)).length }))
|
||||
.filter((item) => item.lines > 500);
|
||||
|
||||
const report = {
|
||||
@ -310,9 +314,9 @@ const sourceLinesOver500 = Number(quality.hygiene?.sourceLinesOver500 ?? 0);
|
||||
|
||||
function esc(value) {
|
||||
return String(value ?? '')
|
||||
.split('\\').join('\\\\')
|
||||
.split('"').join('\\"')
|
||||
.split('\n').join('\\n');
|
||||
.split(String.fromCharCode(92)).join(String.fromCharCode(92, 92))
|
||||
.split('"').join(String.fromCharCode(92) + '"')
|
||||
.split(String.fromCharCode(10)).join(String.fromCharCode(92) + 'n');
|
||||
}
|
||||
|
||||
function labelString(labels) {
|
||||
@ -322,10 +326,16 @@ function labelString(labels) {
|
||||
function fetchCounter(targetStatus) {
|
||||
try {
|
||||
const metrics = execSync(`curl -fsS ${gateway}/metrics`, { encoding: 'utf8' });
|
||||
const re = new RegExp(`platform_quality_gate_runs_total\\{[^}]*suite=\\"${suite}\\"[^}]*status=\\"${targetStatus}\\"[^}]*\\}\\s+(\\d+(?:\\.\\d+)?)`);
|
||||
const match = metrics.match(re);
|
||||
if (!match) return 0;
|
||||
return Number(match[1]);
|
||||
for (const line of metrics.split(String.fromCharCode(10))) {
|
||||
if (
|
||||
line.startsWith('platform_quality_gate_runs_total{') &&
|
||||
line.includes(`suite="${suite}"`) &&
|
||||
line.includes(`status="${targetStatus}"`)
|
||||
) {
|
||||
return Number(line.trim().split(' ').filter(Boolean).pop() || 0);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
} catch {
|
||||
return 0;
|
||||
}
|
||||
@ -392,7 +402,7 @@ const lines = [
|
||||
|
||||
try {
|
||||
execSync(`curl -fsS --data-binary @- ${gateway}/metrics/job/platform-quality-ci/suite/${suite}`, {
|
||||
input: lines.join('\\n'),
|
||||
input: lines.join(String.fromCharCode(10)),
|
||||
stdio: ['pipe', 'inherit', 'inherit']
|
||||
});
|
||||
} catch (error) {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user