Skip to content

Commit e80d306

Browse files
Copilotdavidmurdochjvbriones
authored
Auto-skip release validation columns from PR labels on main release tabs (#231)
* Initial plan * feat: auto-skip release validation from PR labels Co-authored-by: davidmurdoch <187813+davidmurdoch@users.noreply.github.com> * fix: use existing template comments column Co-authored-by: davidmurdoch <187813+davidmurdoch@users.noreply.github.com> * refactor: clarify release sheet row column placeholders Co-authored-by: davidmurdoch <187813+davidmurdoch@users.noreply.github.com> * fix: apply skip logic to both main and release tabs --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: davidmurdoch <187813+davidmurdoch@users.noreply.github.com> Co-authored-by: Javier Briones <1674192+jvbriones@users.noreply.github.com>
1 parent 28b7b9f commit e80d306

1 file changed

Lines changed: 85 additions & 7 deletions

File tree

.github/scripts/post-merge-validation-tracker.mjs

Lines changed: 85 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ const AUTOMATED_TEST_PATTERNS = [
2222
/(^|\/)e2e\//,
2323
/(^|\/)wdio\//
2424
];
25+
const SKIP_RELEASE_VALIDATION_LABEL = 'skip-release-validation';
2526

2627
if (!githubToken) throw new Error('Missing GITHUB_TOKEN env var');
2728
if (!spreadsheetId) throw new Error('Missing SHEET_ID env var');
@@ -223,7 +224,7 @@ async function readRows(authClient, title) {
223224
const res = await sheets.spreadsheets.values.get({
224225
spreadsheetId,
225226
auth: authClient,
226-
range: `${title}!A3:H`,
227+
range: `${title}!A3:J`,
227228
});
228229
return res.data.values || [];
229230
} catch (e) {
@@ -237,7 +238,7 @@ async function appendRows(authClient, title, rows) {
237238
await sheets.spreadsheets.values.append({
238239
spreadsheetId,
239240
auth: authClient,
240-
range: `${title}!A4:H`,
241+
range: `${title}!A4:J`,
241242
valueInputOption: 'USER_ENTERED',
242243
insertDataOption: 'INSERT_ROWS',
243244
requestBody: { values: rows },
@@ -384,6 +385,73 @@ function splitByReleaseAndTitle(items) {
384385
return { relevant, skippedByTitle };
385386
}
386387

388+
function getAutoSkipLabelsForPR(labels, repoName) {
389+
const labelNames = (labels || []).map((label) => label.name).filter(Boolean);
390+
const hasSkipAll = labelNames.includes(SKIP_RELEASE_VALIDATION_LABEL);
391+
392+
const granularLabels = labelNames.filter((name) =>
393+
/^skip-release-validation\[(android|ios|design|chrome|firefox)\]$/i.test(name),
394+
);
395+
396+
const lowerRepoName = String(repoName || '').toLowerCase();
397+
const isMobile = lowerRepoName.endsWith('-mobile');
398+
const isExtension = lowerRepoName.endsWith('-extension');
399+
400+
const validGranularLabels = granularLabels.filter((name) => {
401+
const target = name.toLowerCase();
402+
if (isMobile && (target.includes('[chrome]') || target.includes('[firefox]'))) {
403+
return false;
404+
}
405+
if (isExtension && (target.includes('[android]') || target.includes('[ios]'))) {
406+
return false;
407+
}
408+
return true;
409+
});
410+
411+
return {
412+
hasSkipAll,
413+
validLabels: validGranularLabels,
414+
};
415+
}
416+
417+
function applyAutoSkipToRow(row, labels, repoName) {
418+
419+
const { hasSkipAll, validLabels } = getAutoSkipLabelsForPR(labels, repoName);
420+
if (!hasSkipAll && validLabels.length === 0) {
421+
return row;
422+
}
423+
424+
const updatedRow = [...row];
425+
const validLabelSet = new Set(validLabels.map((label) => label.toLowerCase()));
426+
const isMobile = String(repoName || '').toLowerCase().endsWith('-mobile');
427+
428+
const shouldSkipFirstValidated =
429+
hasSkipAll ||
430+
validLabelSet.has('skip-release-validation[design]') ||
431+
validLabelSet.has(isMobile ? 'skip-release-validation[android]' : 'skip-release-validation[chrome]');
432+
const shouldSkipSecondValidated =
433+
hasSkipAll ||
434+
validLabelSet.has('skip-release-validation[design]') ||
435+
validLabelSet.has(isMobile ? 'skip-release-validation[ios]' : 'skip-release-validation[firefox]');
436+
437+
if (shouldSkipFirstValidated) {
438+
updatedRow[6] = 'Skipped';
439+
}
440+
if (shouldSkipSecondValidated) {
441+
updatedRow[7] = 'Skipped';
442+
}
443+
444+
const labelsForComment = hasSkipAll
445+
? [SKIP_RELEASE_VALIDATION_LABEL, ...validLabels]
446+
: validLabels;
447+
448+
if (shouldSkipFirstValidated || shouldSkipSecondValidated) {
449+
updatedRow[9] = `Release validation automatically skipped due to PR labels: ${labelsForComment.join(', ')}`;
450+
}
451+
452+
return updatedRow;
453+
}
454+
387455
// Add efficient version detection with caching
388456
let versionCache = new Map(); // Cache version bumps per repo
389457

@@ -538,6 +606,10 @@ async function buildTabGrouping(owner, repo, relevantItems, sinceDateISO) {
538606
for (const pr of prs) {
539607
// Check if PR modifies automated test files
540608
const automatedTestsModified = await checkAutomatedTestFiles(owner, repo, pr.number);
609+
const validatedA = '';
610+
const validatedB = '';
611+
const designValidation = '';
612+
const comments = '';
541613

542614
const row = [
543615
makePrHyperlinkCell(pr.html_url, pr.title, pr.number),
@@ -546,10 +618,16 @@ async function buildTabGrouping(owner, repo, relevantItems, sinceDateISO) {
546618
extractSize(pr.labels || []),
547619
automatedTestsModified,
548620
extractTeam(pr.labels || []),
549-
'',
550-
'',
621+
validatedA,
622+
validatedB,
623+
designValidation,
624+
comments,
551625
];
552-
tabToRows.get(title).entries.push({ row, mergedAtIso: pr.closed_at || '' });
626+
tabToRows.get(title).entries.push({
627+
row,
628+
mergedAtIso: pr.closed_at || '',
629+
labels: pr.labels || [],
630+
});
553631
}
554632
}
555633

@@ -736,7 +814,7 @@ async function processTab(authClient, title, entries, platformType) {
736814
const sortedRows = entries
737815
.slice()
738816
.sort((a, b) => new Date(a.mergedAtIso) - new Date(b.mergedAtIso))
739-
.map((e) => e.row);
817+
.map((e) => applyAutoSkipToRow(e.row, e.labels, repo));
740818
const deduped = [];
741819
for (const r of sortedRows) {
742820
const num = parsePrNumberFromCell(r[0]);
@@ -830,4 +908,4 @@ async function main() {
830908
main().catch((e) => {
831909
console.error(e);
832910
process.exit(1);
833-
});
911+
});

0 commit comments

Comments
 (0)