mirror of
https://github.com/microsoft/TypeScript.git
synced 2025-12-12 03:20:56 -06:00
This eliminates a significant number of dependencies, eliminating all npm audit issues, speeding up `npm ci` by 20%, and overall making the build faster (faster startup, direct code is faster than streams, etc) and clearer to understand. I'm finding it much easier to make build changes for the module transform with this; I can more clearly indicate task dependencies and prevent running tasks that don't need to be run. Given we're changing our build process entirely (new deps, new steps), it seems like this is a good time to change things up.
124 lines
5.1 KiB
JavaScript
124 lines
5.1 KiB
JavaScript
import { Octokit } from "@octokit/rest";
|
|
import { runSequence } from "./run-sequence.mjs";
|
|
import fs from "fs";
|
|
import path from "path";
|
|
import url from "url";
|
|
|
|
const __filename = url.fileURLToPath(new URL(import.meta.url));
|
|
const __dirname = path.dirname(__filename);
|
|
|
|
const userName = process.env.GH_USERNAME;
|
|
const reviewers = process.env.REQUESTING_USER ? [process.env.REQUESTING_USER] : ["weswigham", "RyanCavanaugh"];
|
|
const branchName = `pick/${process.env.SOURCE_ISSUE}/${process.env.TARGET_BRANCH}`;
|
|
const remoteUrl = `https://${process.argv[2]}@github.com/${userName}/TypeScript.git`;
|
|
const produceLKG = !!process.env.PRODUCE_LKG;
|
|
|
|
async function main() {
|
|
if (!process.env.TARGET_BRANCH) {
|
|
throw new Error("Target branch not specified");
|
|
}
|
|
if (!process.env.SOURCE_ISSUE) {
|
|
throw new Error("Source issue not specified");
|
|
}
|
|
const currentSha = runSequence([
|
|
["git", ["rev-parse", "HEAD"]]
|
|
]);
|
|
const currentAuthor = runSequence([
|
|
["git", ["log", "-1", `--pretty="%aN <%aE>"`]]
|
|
]);
|
|
|
|
const gh = new Octokit({
|
|
auth: process.argv[2]
|
|
});
|
|
|
|
const inputPR = (await gh.pulls.get({ pull_number: +process.env.SOURCE_ISSUE, owner: "microsoft", repo: "TypeScript" })).data;
|
|
let remoteName = "origin";
|
|
if (inputPR.base.repo.git_url !== `git:github.com/microsoft/TypeScript` && inputPR.base.repo.git_url !== `git://github.com/microsoft/TypeScript`) {
|
|
runSequence([
|
|
["git", ["remote", "add", "nonlocal", inputPR.base.repo.git_url.replace(/^git:(?:\/\/)?/, "https://")]]
|
|
]);
|
|
remoteName = "nonlocal";
|
|
}
|
|
const baseBranchName = inputPR.base.ref;
|
|
runSequence([
|
|
["git", ["fetch", remoteName, baseBranchName]]
|
|
]);
|
|
let logText = runSequence([
|
|
["git", ["log", `${remoteName}/${baseBranchName}..${currentSha.trim()}`, `--pretty="%h %s%n%b"`, "--reverse"]]
|
|
]);
|
|
logText = `Cherry-pick PR #${process.env.SOURCE_ISSUE} into ${process.env.TARGET_BRANCH}
|
|
|
|
Component commits:
|
|
${logText.trim()}`;
|
|
const logpath = path.join(__dirname, "../", "logmessage.txt");
|
|
const mergebase = runSequence([["git", ["merge-base", `${remoteName}/${baseBranchName}`, currentSha]]]).trim();
|
|
runSequence([
|
|
["git", ["checkout", "-b", "temp-branch"]],
|
|
["git", ["reset", mergebase, "--soft"]]
|
|
]);
|
|
fs.writeFileSync(logpath, logText);
|
|
runSequence([
|
|
["git", ["commit", "-F", logpath, `--author="${currentAuthor.trim()}"`]]
|
|
]);
|
|
fs.unlinkSync(logpath);
|
|
const squashSha = runSequence([
|
|
["git", ["rev-parse", "HEAD"]]
|
|
]);
|
|
runSequence([
|
|
["git", ["checkout", process.env.TARGET_BRANCH]], // checkout the target branch
|
|
["git", ["checkout", "-b", branchName]], // create a new branch
|
|
["git", ["cherry-pick", squashSha.trim()]],
|
|
]);
|
|
if (produceLKG) {
|
|
runSequence([
|
|
["node", ["./node_modules/hereby/dist/cli.js", "LKG"]],
|
|
["git", ["add", "lib"]],
|
|
["git", ["commit", "-m", `"Update LKG"`]]
|
|
]);
|
|
}
|
|
runSequence([
|
|
["git", ["remote", "add", "fork", remoteUrl]], // Add the remote fork
|
|
["git", ["push", "--set-upstream", "fork", branchName, "-f"]] // push the branch
|
|
]);
|
|
|
|
const r = await gh.pulls.create({
|
|
owner: "Microsoft",
|
|
repo: "TypeScript",
|
|
maintainer_can_modify: true,
|
|
title: `🤖 Pick PR #${process.env.SOURCE_ISSUE} (${inputPR.title.substring(0, 35)}${inputPR.title.length > 35 ? "..." : ""}) into ${process.env.TARGET_BRANCH}`,
|
|
head: `${userName}:${branchName}`,
|
|
base: process.env.TARGET_BRANCH,
|
|
body:
|
|
`This cherry-pick was triggered by a request on https://github.com/Microsoft/TypeScript/pull/${process.env.SOURCE_ISSUE}
|
|
Please review the diff and merge if no changes are unexpected.${produceLKG ? ` An LKG update commit is included separately from the base change.` : ""}
|
|
You can view the cherry-pick log [here](https://typescript.visualstudio.com/TypeScript/_build/index?buildId=${process.env.BUILD_BUILDID}&_a=summary).
|
|
|
|
cc ${reviewers.map(r => "@" + r).join(" ")}`,
|
|
});
|
|
const num = r.data.number;
|
|
console.log(`Pull request ${num} created.`);
|
|
|
|
await gh.issues.createComment({
|
|
issue_number: +process.env.SOURCE_ISSUE,
|
|
owner: "Microsoft",
|
|
repo: "TypeScript",
|
|
body: `Hey @${process.env.REQUESTING_USER}, I've opened #${num} for you.`
|
|
});
|
|
}
|
|
|
|
main().catch(async e => {
|
|
console.error(e);
|
|
process.exitCode = 1;
|
|
if (process.env.SOURCE_ISSUE) {
|
|
const gh = new Octokit({
|
|
auth: process.argv[2]
|
|
});
|
|
await gh.issues.createComment({
|
|
issue_number: +process.env.SOURCE_ISSUE,
|
|
owner: "Microsoft",
|
|
repo: "TypeScript",
|
|
body: `Hey @${process.env.REQUESTING_USER}, I couldn't open a PR with the cherry-pick. ([You can check the log here](https://typescript.visualstudio.com/TypeScript/_build/index?buildId=${process.env.BUILD_BUILDID}&_a=summary)). You may need to squash and pick this PR into ${process.env.TARGET_BRANCH} manually.`
|
|
});
|
|
}
|
|
});
|