Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
{
"changes": [
{
"packageName": "@microsoft/rush",
"comment": "Add performance measures around various operations, include performance entries in telemetry payload.",
"type": "none"
}
],
"packageName": "@microsoft/rush"
}
2 changes: 2 additions & 0 deletions common/reviews/api/rush-lib.api.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import { JsonNull } from '@rushstack/node-core-library';
import { JsonObject } from '@rushstack/node-core-library';
import { LookupByPath } from '@rushstack/lookup-by-path';
import { PackageNameParser } from '@rushstack/node-core-library';
import type { PerformanceEntry as PerformanceEntry_2 } from 'node:perf_hooks';
import type { StdioSummarizer } from '@rushstack/terminal';
import { SyncHook } from 'tapable';
import { SyncWaterfallHook } from 'tapable';
Expand Down Expand Up @@ -884,6 +885,7 @@ export interface ITelemetryData {
readonly machineInfo?: ITelemetryMachineInfo;
readonly name: string;
readonly operationResults?: Record<string, ITelemetryOperationResult>;
readonly performanceEntries?: readonly PerformanceEntry_2[];
readonly platform?: string;
readonly result: 'Succeeded' | 'Failed';
readonly rushVersion?: string;
Expand Down
4 changes: 3 additions & 1 deletion libraries/rush-lib/src/api/Rush.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import { CommandLineMigrationAdvisor } from '../cli/CommandLineMigrationAdvisor'
import { EnvironmentVariableNames } from './EnvironmentConfiguration';
import type { IBuiltInPluginConfiguration } from '../pluginFramework/PluginLoader/BuiltInPluginLoader';
import { RushPnpmCommandLine } from '../cli/RushPnpmCommandLine';
import { measureAsyncFn } from '../utilities/performance';

/**
* Options to pass to the rush "launch" functions.
Expand Down Expand Up @@ -93,8 +94,9 @@ export class Rush {
alreadyReportedNodeTooNewError: options.alreadyReportedNodeTooNewError,
builtInPluginConfigurations: options.builtInPluginConfigurations
});
// CommandLineParser.executeAsync() should never reject the promise
// eslint-disable-next-line no-console
parser.executeAsync().catch(console.error); // CommandLineParser.executeAsync() should never reject the promise
measureAsyncFn('rush:parser:executeAsync', () => parser.executeAsync()).catch(console.error);
}

/**
Expand Down
8 changes: 6 additions & 2 deletions libraries/rush-lib/src/cli/RushCommandLineParser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,8 @@ import { InstallAutoinstallerAction } from './actions/InstallAutoinstallerAction
import { LinkPackageAction } from './actions/LinkPackageAction';
import { BridgePackageAction } from './actions/BridgePackageAction';

import { measureAsyncFn } from '../utilities/performance';

/**
* Options for `RushCommandLineParser`.
*/
Expand Down Expand Up @@ -219,7 +221,9 @@ export class RushCommandLineParser extends CommandLineParser {
this._terminalProvider.verboseEnabled = this._terminalProvider.debugEnabled =
process.argv.indexOf('--debug') >= 0;

await this.pluginManager.tryInitializeUnassociatedPluginsAsync();
await measureAsyncFn('rush:initializeUnassociatedPlugins', () =>
this.pluginManager.tryInitializeUnassociatedPluginsAsync()
);

return await super.executeAsync(args);
}
Expand Down Expand Up @@ -298,7 +302,7 @@ export class RushCommandLineParser extends CommandLineParser {
}

try {
await super.onExecuteAsync();
await measureAsyncFn('rush:commandLineParser:onExecuteAsync', () => super.onExecuteAsync());
} finally {
if (this.telemetry) {
this.flushTelemetry();
Expand Down
7 changes: 5 additions & 2 deletions libraries/rush-lib/src/cli/actions/BaseInstallAction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import { SUBSPACE_LONG_ARG_NAME, type SelectionParameterSet } from '../parsing/S
import type { RushConfigurationProject } from '../../api/RushConfigurationProject';
import type { Subspace } from '../../api/Subspace';
import { getVariantAsync, VARIANT_PARAMETER } from '../../api/Variants';
import { measureAsyncFn } from '../../utilities/performance';

/**
* Temporary data structure used by `BaseInstallAction.runAsync()`
Expand Down Expand Up @@ -285,7 +286,9 @@ export abstract class BaseInstallAction extends BaseRushAction {
installSuccessful = false;
throw error;
} finally {
await purgeManager.startDeleteAllAsync();
await measureAsyncFn('rush:installManager:startDeleteAllAsync', () =>
purgeManager.startDeleteAllAsync()
);
stopwatch.stop();

this._collectTelemetry(stopwatch, installManagerOptions, installSuccessful);
Expand Down Expand Up @@ -327,7 +330,7 @@ export abstract class BaseInstallAction extends BaseRushAction {
installManagerOptions
);

await installManager.doInstallAsync();
await measureAsyncFn('rush:installManager:doInstallAsync', () => installManager.doInstallAsync());
}

private _collectTelemetry(
Expand Down
19 changes: 13 additions & 6 deletions libraries/rush-lib/src/cli/actions/BaseRushAction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@ import { Utilities } from '../../utilities/Utilities';
import type { RushGlobalFolder } from '../../api/RushGlobalFolder';
import type { RushSession } from '../../pluginFramework/RushSession';
import type { IRushCommand } from '../../pluginFramework/RushLifeCycle';
import { measureAsyncFn } from '../../utilities/performance';

const PERF_PREFIX: string = 'rush:action';

export interface IBaseRushActionOptions extends ICommandLineActionOptions {
/**
Expand Down Expand Up @@ -75,7 +78,7 @@ export abstract class BaseConfiglessRushAction extends CommandLineAction impleme
this.terminal.write(`Starting "rush ${this.actionName}"\n`);
}

return await this.runAsync();
await measureAsyncFn(`${PERF_PREFIX}:runAsync`, () => this.runAsync());
}

/**
Expand Down Expand Up @@ -121,15 +124,19 @@ export abstract class BaseRushAction extends BaseConfiglessRushAction {

this._throwPluginErrorIfNeed();

await this.parser.pluginManager.tryInitializeAssociatedCommandPluginsAsync(this.actionName);
await measureAsyncFn(`${PERF_PREFIX}:initializePluginsAsync`, () =>
this.parser.pluginManager.tryInitializeAssociatedCommandPluginsAsync(this.actionName)
);

this._throwPluginErrorIfNeed();

const { hooks: sessionHooks } = this.rushSession;
if (sessionHooks.initialize.isUsed()) {
// Avoid the cost of compiling the hook if it wasn't tapped.
await sessionHooks.initialize.promise(this);
}
await measureAsyncFn(`${PERF_PREFIX}:initializePlugins`, async () => {
if (sessionHooks.initialize.isUsed()) {
// Avoid the cost of compiling the hook if it wasn't tapped.
await sessionHooks.initialize.promise(this);
}
});

return super.onExecuteAsync();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import { Utilities } from '../../utilities/Utilities';
import { Stopwatch } from '../../utilities/Stopwatch';
import { Autoinstaller } from '../../logic/Autoinstaller';
import type { IGlobalCommandConfig, IShellCommandTokenContext } from '../../api/CommandLineConfiguration';
import { measureAsyncFn } from '../../utilities/performance';

/**
* Constructor parameters for GlobalScriptAction.
Expand Down Expand Up @@ -120,7 +121,9 @@ export class GlobalScriptAction extends BaseScriptAction<IGlobalCommandConfig> {
this.commandLineConfiguration?.additionalPathFolders.slice() || [];

if (this._autoinstallerName) {
await this._prepareAutoinstallerNameAsync();
await measureAsyncFn('rush:globalScriptAction:prepareAutoinstaller', () =>
this._prepareAutoinstallerNameAsync()
);

const autoinstallerNameBinPath: string = path.join(this._autoinstallerFullPath, 'node_modules', '.bin');
additionalPathFolders.push(autoinstallerNameBinPath);
Expand Down
Loading
Loading