Pretty old question, but still the answer might help someone in the future.
I found 2 options to run other SFDX commands without messing around with CLI and child processes.
Option 1: Inheritance
Since all the commands are actually Typescript classes, you can extend a command and then just call super.run()
. E.g.:
import { ApexTestRunCommand } from 'salesforce-alm/dist/commands/force/apex/test/run';
...
export default class TestDXApexTestRunCommand extends ApexTestRunCommand {
...
public async run(): Promise<unknown> {
await this.normalizeFlags();
const testRunResult = await super.run();
if (testRunResult && this.isToGenerateHtmlReport) {
this.generateHtmlReport(testRunResult as Report);
}
return testRunResult;
}
...
}
This code was composed before the saleseforce-alm
plugin has been split, but the idea works even with the new plugin composition. Just import like this:
import Report from "@salesforce/plugin-apex/lib/commands/force/apex/test/report";
Option 2: Construct and call
This one took some time to figure out. You can construct a command and then run it, but you may see, that flags are undefined for the run. This is because SFDX CLI does not call directly the run
method after construction. First, it parses the arguments and does some initialization. Fortunately, this whole logic is encapsulated in the _run
method. So you can just call that method instead:
import Report from "@salesforce/plugin-apex/lib/commands/force/apex/test/report";
...
export default class AllureReport extends SfdxCommand {
...
public async run(): Promise<AnyJson> {
const config: any = {};
const reportCmd = new Report(["-i", testRunId], config);
return reportCmd._run();
}
}