mirror of
https://github.com/storybookjs/storybook.git
synced 2025-04-06 23:51:16 +08:00
106 lines
3.3 KiB
TypeScript
106 lines
3.3 KiB
TypeScript
import { program } from 'commander';
|
|
// eslint-disable-next-line depend/ban-dependencies
|
|
import ora from 'ora';
|
|
import { v4 as uuidv4 } from 'uuid';
|
|
|
|
import { esMain } from '../utils/esmain';
|
|
import { getPullInfoFromCommits, getRepo } from './utils/get-changes';
|
|
import { getLatestTag, git } from './utils/git-client';
|
|
import { getLabelIds, getUnpickedPRs, githubGraphQlClient } from './utils/github-client';
|
|
|
|
program
|
|
.name('label-patches')
|
|
.description('Label all patches applied in current branch up to the latest release tag.')
|
|
.option(
|
|
'-A, --all',
|
|
'Label all pull requests pending patches, iregardless if they are in the git log or not',
|
|
false
|
|
);
|
|
|
|
async function labelPR(id: string, labelId: string) {
|
|
await githubGraphQlClient(
|
|
`
|
|
mutation ($input: AddLabelsToLabelableInput!) {
|
|
addLabelsToLabelable(input: $input) {
|
|
clientMutationId
|
|
}
|
|
}
|
|
`,
|
|
{ input: { labelIds: [labelId], labelableId: id, clientMutationId: uuidv4() } }
|
|
);
|
|
}
|
|
|
|
async function getPullRequestsFromLog({ repo }: { repo: string }) {
|
|
const spinner = ora('Looking for latest tag').start();
|
|
const latestTag = await getLatestTag();
|
|
spinner.succeed(`Found latest tag: ${latestTag}`);
|
|
|
|
const spinner2 = ora(`Looking at cherry pick commits since ${latestTag}`).start();
|
|
const commitsSinceLatest = await git.log({ from: latestTag });
|
|
console.log(commitsSinceLatest);
|
|
const cherryPicked = commitsSinceLatest.all.flatMap((it) => {
|
|
const result = it.body.match(/\(cherry picked from commit (\b[0-9a-f]{7,40}\b)\)/);
|
|
return result ? [result?.[1]] : [];
|
|
});
|
|
|
|
if (cherryPicked.length === 0) {
|
|
spinner2.fail('No cherry pick commits found to label.');
|
|
return [];
|
|
}
|
|
const pullRequests = (
|
|
await getPullInfoFromCommits({
|
|
repo,
|
|
commits: cherryPicked.map((hash) => ({ hash })),
|
|
})
|
|
).filter((it) => it.id != null);
|
|
|
|
if (pullRequests.length === 0) {
|
|
spinner2.fail(
|
|
`Found picks: ${cherryPicked.join(', ')}, but no associated pull request found to label.`
|
|
);
|
|
return pullRequests;
|
|
}
|
|
|
|
const commitWithPr = pullRequests.map((pr) => `Commit: ${pr.commit}\n PR: ${pr.links.pull}`);
|
|
|
|
spinner2.succeed(`Found the following picks 🍒:\n ${commitWithPr.join('\n')}`);
|
|
|
|
return pullRequests;
|
|
}
|
|
|
|
export const run = async (options: unknown) => {
|
|
if (!process.env.GH_TOKEN) {
|
|
throw new Error('GH_TOKEN environment variable must be set, exiting.');
|
|
}
|
|
|
|
const repo = await getRepo();
|
|
const labelAll = typeof options === 'object' && 'all' in options && Boolean(options.all);
|
|
|
|
const pullRequestsToLabel = labelAll
|
|
? await getUnpickedPRs('next')
|
|
: await getPullRequestsFromLog({ repo });
|
|
if (pullRequestsToLabel.length === 0) {
|
|
return;
|
|
}
|
|
|
|
const spinner3 = ora(
|
|
`Labeling ${pullRequestsToLabel.length} PRs with the patch:done label...`
|
|
).start();
|
|
try {
|
|
const labelToId = await getLabelIds({ repo, labelNames: ['patch:done'] });
|
|
await Promise.all(pullRequestsToLabel.map((pr) => labelPR(pr.id, labelToId['patch:done'])));
|
|
spinner3.succeed(`Successfully labeled all PRs with the patch:done label.`);
|
|
} catch (e) {
|
|
spinner3.fail(`Something went wrong when labelling the PRs.`);
|
|
console.error(e);
|
|
}
|
|
};
|
|
|
|
if (esMain(import.meta.url)) {
|
|
const options = program.parse().opts();
|
|
run(options).catch((err) => {
|
|
console.error(err);
|
|
process.exit(1);
|
|
});
|
|
}
|