From 30b687f46d3c24b232c6614eeb801ccee65dddf0 Mon Sep 17 00:00:00 2001 From: Martin Hochel Date: Wed, 29 Mar 2023 13:30:40 +0200 Subject: [PATCH 1/2] feat(scripts-executors): support custom base and printing all affected packages for checkIfPackagesAffected --- scripts/executors/checkIfPackagesAffected.js | 43 +++++++++----------- scripts/monorepo/src/getAffectedPackages.js | 17 ++++++++ scripts/monorepo/src/index.d.ts | 2 +- scripts/monorepo/src/utils.js | 36 +++++++++++++++- 4 files changed, 72 insertions(+), 26 deletions(-) diff --git a/scripts/executors/checkIfPackagesAffected.js b/scripts/executors/checkIfPackagesAffected.js index da03b35904499b..ec09a15f7096bc 100644 --- a/scripts/executors/checkIfPackagesAffected.js +++ b/scripts/executors/checkIfPackagesAffected.js @@ -1,41 +1,36 @@ -const { getAffectedPackages, getNthCommit } = require('@fluentui/scripts-monorepo'); +const { getAffectedPackages } = require('@fluentui/scripts-monorepo'); const yargs = require('yargs'); const args = yargs - .option('packages', { + .option('package', { alias: 'p', type: 'array', + // eslint-disable-next-line @typescript-eslint/naming-convention + string: true, description: 'Package to check modified files from', - demandOption: true, + demandOption: false, }) - .option('pr', { - alias: 'r', - type: 'boolean', - description: 'During PR build compares to origin/master, in CI build compares to last commit', - default: false, + .option('base', { + type: 'string', + description: 'Base of the current branch (usually main or master)', + default: 'origin/master', }) - .scriptName('bundle-size') .version(false).argv; const isPackageAffected = () => { - const { packages, pr } = args; + const { package: packages, base } = args; + const affectedPackages = getAffectedPackages(base); - let affectedPackages = new Set(); - - if (pr) { - affectedPackages = getAffectedPackages(); - } else { - // master CI build, - const previousMasterCommit = getNthCommit(); - affectedPackages = getAffectedPackages(previousMasterCommit); - } - - for (const pkg of packages) { - if (affectedPackages.has(pkg)) { - return true; + if (packages) { + for (const pkg of packages) { + if (affectedPackages.has(pkg)) { + return true; + } } + return false; } - return false; + + return affectedPackages; }; function main() { diff --git a/scripts/monorepo/src/getAffectedPackages.js b/scripts/monorepo/src/getAffectedPackages.js index 1bedc5046a0803..7546395da18493 100644 --- a/scripts/monorepo/src/getAffectedPackages.js +++ b/scripts/monorepo/src/getAffectedPackages.js @@ -1,6 +1,7 @@ const { spawnSync } = require('child_process'); const findGitRoot = require('./findGitRoot'); +const { getUncommittedFiles, getUntrackedFiles } = require('./utils'); /** * Indicator of what packages have been affected by changes @@ -10,6 +11,7 @@ const findGitRoot = require('./findGitRoot'); * @returns {Set} - Set of packages that are affected by in the current branch */ function getAffectedPackages(since = 'origin/master') { + reportLageAffectedSinceResolution(); const gitRoot = findGitRoot(); const res = spawnSync('yarn', ['lage', 'info', '--since', since], { cwd: gitRoot, shell: true }); if (res.status !== 0) { @@ -28,4 +30,19 @@ function getAffectedPackages(since = 'origin/master') { return new Set(info.scope); } +/** + * @see https://github.com/microsoft/fluentui/issues/26147 + */ +function reportLageAffectedSinceResolution() { + const uncommittedGitFiles = [...getUncommittedFiles(), ...getUntrackedFiles()]; + if (uncommittedGitFiles.length > 0) { + console.warn( + '⚠️ NOTE:\n', + 'You workspace contains uncommitted or untracked files!\n', + 'This gives you false positives about true affected tree.\n', + 'To get proper results make sure you have clean git tree.\n\n', + ); + } +} + exports.getAffectedPackages = getAffectedPackages; diff --git a/scripts/monorepo/src/index.d.ts b/scripts/monorepo/src/index.d.ts index 2a4c56adac346c..ee8b3d4e5ca0df 100644 --- a/scripts/monorepo/src/index.d.ts +++ b/scripts/monorepo/src/index.d.ts @@ -7,6 +7,6 @@ export { isConvergedPackage, shipsAMD } from './isConvergedPackage'; export { getAffectedPackages } from './getAffectedPackages'; export { getLernaAliases } from './get-lerna-aliases'; export { getDefaultEnvironmentVars } from './getDefaultEnvironmentVars'; -export { getProjectMetadata, workspaceRoot } from './utils'; +export { getProjectMetadata, workspaceRoot, getUncommittedFiles, getUntrackedFiles } from './utils'; export * as eslintConstants from './eslint-constants'; export { getNthCommit } from './getNthCommit'; diff --git a/scripts/monorepo/src/utils.js b/scripts/monorepo/src/utils.js index 6f4c813a25fd59..a3fe6c5457987a 100644 --- a/scripts/monorepo/src/utils.js +++ b/scripts/monorepo/src/utils.js @@ -1,8 +1,11 @@ +const { execSync } = require('child_process'); const fs = require('fs'); const path = require('path'); -const { workspaceRoot } = require('nx/src/utils/app-root'); + +const { workspaceRoot } = require('@nrwl/devkit'); const findGitRoot = require('./findGitRoot'); +const TEN_MEGABYTES = 1024 * 10000; /** * Gets project metadata from monorepo source of truth which is `workspace.json` @@ -20,5 +23,36 @@ function getProjectMetadata(options) { return nxWorkspace.projects[options.name]; } +/** + * + * @param {string} command + * @returns {string[]} + */ +function parseGitOutput(command) { + return execSync(command, { maxBuffer: TEN_MEGABYTES, cwd: workspaceRoot }) + .toString('utf-8') + .split('\n') + .map(a => a.trim()) + .filter(a => a.length > 0); +} + +/** + * + * @returns {string[]} + */ +function getUncommittedFiles() { + return parseGitOutput(`git diff --name-only --no-renames --relative HEAD .`); +} + +/** + * + * @returns {string[]} + */ +function getUntrackedFiles() { + return parseGitOutput(`git ls-files --others --exclude-standard`); +} + +exports.getUncommittedFiles = getUncommittedFiles; +exports.getUntrackedFiles = getUntrackedFiles; exports.getProjectMetadata = getProjectMetadata; exports.workspaceRoot = workspaceRoot; From 7c0bbf542427570a5a2dd5e36f65a7aebe17e6b7 Mon Sep 17 00:00:00 2001 From: Martin Hochel Date: Wed, 29 Mar 2023 13:31:19 +0200 Subject: [PATCH 2/2] ci: update check:affected-packages API to check:affected --- .devops/templates/runpublishvrscreenshot.yml | 2 +- azure-pipelines.perf-test.yml | 6 +++--- package.json | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.devops/templates/runpublishvrscreenshot.yml b/.devops/templates/runpublishvrscreenshot.yml index 199504680c4ba3..ac66886c6fb176 100644 --- a/.devops/templates/runpublishvrscreenshot.yml +++ b/.devops/templates/runpublishvrscreenshot.yml @@ -19,7 +19,7 @@ steps: isPR=${{lower(eq(variables['Build.Reason'], 'PullRequest'))}} echo $isPR if [[ $isPR == true ]]; then - packageAffected=$(yarn --silent check:affected-package --packages ${{ parameters.vrTestPackageName }} --pr=true) + packageAffected=$(yarn --silent check:affected --package ${{ parameters.vrTestPackageName }}) if [[ $packageAffected == false ]]; then echo "In PR pipeline but NOT affecting test package. Skipping test run" echo "##vso[task.setvariable variable=vrTestSkip;]yes" diff --git a/azure-pipelines.perf-test.yml b/azure-pipelines.perf-test.yml index 08682210e8c386..c0662c3d9b1f18 100644 --- a/azure-pipelines.perf-test.yml +++ b/azure-pipelines.perf-test.yml @@ -21,9 +21,9 @@ jobs: displayName: yarn - script: | - NorthstarAffected=$(yarn --silent check:affected-package --packages @fluentui/react-northstar --pr) - V8Affected=$(yarn --silent check:affected-package --packages @fluentui/react --pr) - ReactComponentsAffected=$(yarn --silent check:affected-package --packages @fluentui/react-components --pr) + NorthstarAffected=$(yarn --silent check:affected --package @fluentui/react-northstar) + V8Affected=$(yarn --silent check:affected --package @fluentui/react) + ReactComponentsAffected=$(yarn --silent check:affected --package @fluentui/react-components) if [[ $NorthstarAffected == true ]]; then echo "##vso[task.setvariable variable=NorthstarPackageAffected;isOutput=true]true" fi diff --git a/package.json b/package.json index bfab1faa390f91..12d49f6b292c6f 100644 --- a/package.json +++ b/package.json @@ -23,7 +23,7 @@ "change": "beachball change --no-commit", "check:change": "beachball check", "check:modified-files": "node -r ./scripts/ts-node/register ./scripts/executors/check-for-modified-files", - "check:affected-package": "node ./scripts/executors/checkIfPackagesAffected.js", + "check:affected": "node ./scripts/executors/checkIfPackagesAffected.js", "check:installed-dependencies-versions": "satisfied --no-peers --skip-invalid", "clean": "lage clean --verbose", "code-style": "lage code-style --verbose",