Skip to content

Commit

Permalink
feat: add package1:version:create command
Browse files Browse the repository at this point in the history
  • Loading branch information
WillieRuemmele committed Jul 28, 2022
1 parent 41cc637 commit 15636a0
Show file tree
Hide file tree
Showing 7 changed files with 349 additions and 13 deletions.
4 changes: 0 additions & 4 deletions messages/default.md
Original file line number Diff line number Diff line change
Expand Up @@ -887,10 +887,6 @@ Minutes to wait for the package version to be created. The default is 2 minutes.

Field %s must contain only a numeric value: %s.

# package1VersionCreateCommandInvalidVersion

Version supplied, %s, is not formatted correctly. Enter in major.minor format, for example, 3.2.

# package1VersionCreateCommandTimeout

Stopped waiting for package upload to finish. Wait time exceeded. waitTimeInMinutes = %s.
Expand Down
4 changes: 4 additions & 0 deletions messages/package1_version_create.md
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,10 @@ Package version creation failed with unknown error

Successfully created package version: %s for package %s.

# package1VersionCreateCommandInvalidVersion

Version supplied, %s, is not formatted correctly. Enter in major.minor format, for example, 3.2.

# SUCCESS

Successfully uploaded package [%s]
Expand Down
8 changes: 5 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
"@salesforce/command": "^5.2.1",
"@salesforce/core": "^3.24.0",
"@salesforce/kit": "^1.5.44",
"@salesforce/packaging": "^0.0.9",
"@salesforce/packaging": "^0.0.11",
"tslib": "^2"
},
"devDependencies": {
Expand All @@ -21,6 +21,7 @@
"@salesforce/dev-scripts": "^1.0.4",
"@salesforce/plugin-command-reference": "^1.3.20",
"@salesforce/plugin-config": "^1.4.12",
"@salesforce/plugin-auth": "^2.2.3",
"@salesforce/prettier-config": "^0.0.2",
"@salesforce/ts-sinon": "1.3.21",
"@salesforce/ts-types": "^1.5.20",
Expand Down Expand Up @@ -84,7 +85,8 @@
"@oclif/plugin-help",
"@oclif/plugin-command-snapshot",
"@salesforce/plugin-command-reference",
"@salesforce/plugin-config"
"@salesforce/plugin-config",
"@salesforce/plugin-auth"
],
"plugins": [
"@oclif/plugin-version"
Expand Down Expand Up @@ -181,7 +183,7 @@
"test:command-reference": "./bin/run commandreference:generate --erroronwarnings",
"test:deprecation-policy": "./bin/run snapshot:compare",
"test:nuts": "nyc mocha \"**/*.nut.ts\" --slow 4500 --timeout 600000 --parallel",
"test:nuts:package1": "nyc mocha \"**/package1/*.nut.ts\" --slow 4500 --timeout 600000 --parallel",
"test:nuts:package1": "nyc mocha \"**/package1/*.nut.ts\" --slow 4500 --timeout 600000",
"version": "oclif readme"
},
"publishConfig": {
Expand Down
2 changes: 1 addition & 1 deletion src/commands/force/package1/beta/version/create.ts
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ export class Package1VersionCreateCommand extends SfdxCommand {
};

public async run(): Promise<
Pick<PackagingSObjects.PackageUploadRequest, 'Status' & 'Id' & 'MetadataPackageId' & 'MetadataPackageVersionId'>
Pick<PackagingSObjects.PackageUploadRequest, 'Status' | 'Id' | 'MetadataPackageId' | 'MetadataPackageVersionId'>
> {
const version = this.parseVersion(this.flags.version);
if (this.flags.wait) {
Expand Down
101 changes: 101 additions & 0 deletions test/commands/force/package1/versionCreate.nut.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
/*
* Copyright (c) 2022, salesforce.com, inc.
* All rights reserved.
* Licensed under the BSD 3-Clause license.
* For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause
*/

import * as path from 'path';
import * as fs from 'fs';
import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit';
import { expect } from 'chai';
import { PackagingSObjects } from '@salesforce/packaging';
import { sleep } from '@salesforce/kit';

const pollUntilComplete = async (id: string): Promise<PackagingSObjects.PackageUploadRequest> => {
const result = execCmd<PackagingSObjects.PackageUploadRequest>(
`force:package1:beta:version:create:get -i ${id} -u 1gp --json`,
{ ensureExitCode: 0 }
).jsonOutput.result;
if (result.Status === 'SUCCESS') {
return result;
} else {
await sleep(5000);
await pollUntilComplete(id);
}
};

describe.only('package1:version:create', () => {
let session: TestSession;
let packageId: string;
before(async () => {
if (!process.env.ONEGP_TESTKIT_AUTH_URL) {
throw new Error('"ONEGP_TESTKIT_AUTH_URL" env var required for 1gp NUTs');
}
const authPath = path.join(process.cwd(), 'authUrl.txt');
await fs.promises.writeFile(authPath, process.env.ONEGP_TESTKIT_AUTH_URL, 'utf8');
const executablePath = path.join(process.cwd(), 'bin', 'dev');
session = await TestSession.create({
setupCommands: [`${executablePath} auth:sfdxurl:store -f ${authPath} -a 1gp`],
project: { name: 'package1VersionDisplay' },
});
packageId = '03346000000MrC0AAK'; // once version:list PR is merged execCmd('package1:beta:version:list -u 1gp').jsonOutput.result[0].MetadataPackageId;
});

after(async () => {
await fs.promises.rm('authUrl.txt');
await session?.clean();
});

// we need to the run the synchronous command first, to avoid duplicate package version create API requests in the NUTs
it(`should create a new 1gp package version for package id ${packageId} and wait`, function () {
const command = `force:package1:beta:version:create -n 1gpPackageNUT -i ${packageId} -w 5 -u 1gp`;
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout as string;
expect(output.trim()).to.match(/Package upload is enqueued\. Waiting \d+ more seconds/);
expect(output.trim()).to.match(/Package upload is in progress\. Waiting \d+ more seconds/);
expect(output.trim()).to.match(/Successfully uploaded package \[04t.*]/);
});

it(`should create a new 1gp package version for package id ${packageId} and wait (json)`, function () {
const command = `force:package1:beta:version:create -n 1gpPackageNUT -i ${packageId} --json -w 5 -u 1gp`;
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
const output = execCmd<
Pick<PackagingSObjects.PackageUploadRequest, 'Status' | 'Id' | 'MetadataPackageId' | 'MetadataPackageVersionId'>
>(command, { ensureExitCode: 0 }).jsonOutput.result;
expect(output.Status).to.equal('SUCCESS');
expect(output.Id).to.be.a('string');
expect(output.MetadataPackageId).to.be.a('string');
expect(output.MetadataPackageVersionId).to.be.a('string');
expect(output.MetadataPackageVersionId.startsWith('04t')).to.be.true;
expect(output.MetadataPackageId.startsWith('033')).to.be.true;
});

it(`should create a new 1gp package version for package id ${packageId} without waiting`, async function () {
const command = `force:package1:beta:version:create -n 1gpPackageNUT -i ${packageId} -u 1gp`;
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout as string;
expect(output).to.match(/PackageUploadRequest has been enqueued\./);
// sfdx force:package1:beta:version:create:get -i 0HD4p000000blVAGAY -u admin@integrationtestrelorgna40.org
expect(output).to.match(/sfdx force:package1:beta:version:create:get -i 0HD.* -u/);
// ensure the package has uploaded by waiting for the package report to be done
const requestId = /0HD\w*/.exec(output)[0];
await pollUntilComplete(requestId);
});

it(`should create a new 1gp package version for package id ${packageId} (json)`, async function () {
const command = `force:package1:beta:version:create -n 1gpPackageNUT -i ${packageId} --json -u 1gp`;
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
const output = execCmd<
Pick<PackagingSObjects.PackageUploadRequest, 'Status' | 'Id' | 'MetadataPackageId' | 'MetadataPackageVersionId'>
>(command, { ensureExitCode: 0 }).jsonOutput.result;
expect(output.Status).to.equal('QUEUED');
expect(output.Id).to.be.a('string');
expect(output.MetadataPackageId).to.be.a('string');
expect(output.MetadataPackageVersionId).to.be.a('string');
expect(output.MetadataPackageVersionId.startsWith('04t')).to.be.true;
expect(output.MetadataPackageId.startsWith('033')).to.be.true;
// ensure the package has uploaded by waiting for the package report to be done
await pollUntilComplete(output.Id);
});
});
111 changes: 111 additions & 0 deletions test/commands/force/package1/versionCreate.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
/*
* Copyright (c) 2020, salesforce.com, inc.
* All rights reserved.
* Licensed under the BSD 3-Clause license.
* For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause
*/
import { Org } from '@salesforce/core';
import { testSetup } from '@salesforce/core/lib/testSetup';
import { fromStub, stubInterface, stubMethod } from '@salesforce/ts-sinon';
import { Config } from '@oclif/core';
import { assert, expect } from 'chai';
import { Package1VersionCreateCommand } from '../../../../src/commands/force/package1/beta/version/create';

const $$ = testSetup();
const oclifConfigStub = fromStub(stubInterface<Config>($$.SANDBOX));
let uxStub: sinon.SinonStub;

class TestCommand extends Package1VersionCreateCommand {
public async runIt() {
await this.init();
uxStub = stubMethod($$.SANDBOX, this.ux, 'log');
return this.run();
}
public setOrg(org: Org) {
this.org = org;
}
}

const runCmd = async (params: string[], result: string, errors?: { errors: Error[] }) => {
const cmd = new TestCommand(params, oclifConfigStub);
stubMethod($$.SANDBOX, cmd, 'assignOrg').callsFake(() => {
const orgStub = fromStub(
stubInterface<Org>($$.SANDBOX, {
getUsername: () => 'test@user.com',
getConnection: () => {
return {
tooling: {
sobject: () => {
return {
create: () => ({ id: '0HD4p000000blUvGXX' }),
retrieve: () => ({
Status: result,
MetadataPackageVersionId: '04t4p000002BavTXXX',
Errors: errors,
Id: '0HD4p000000blUvGXX',
MetadataPackageId: '03346000000MrC0AXX',
}),
};
},
},
};
},
})
);
cmd.setOrg(orgStub);
});
const res = cmd.runIt();

return res;
};

describe('force:package1:version:create', () => {
afterEach(() => {
$$.SANDBOX.restore();
});

it('should print SUCCESS status correctly', async () => {
const result = await runCmd(['--packageid', '03346000000MrC0AXX', '--name', 'test'], 'SUCCESS');
expect(result.Status).to.equal('SUCCESS');
expect(uxStub.callCount).to.equal(1);
expect(uxStub.firstCall.args[0]).to.equal('Successfully uploaded package [04t4p000002BavTXXX]');
});

it('should print QUEUED status correctly', async () => {
const result = await runCmd(['--packageid', '03346000000MrC0AXX', '--name', 'test'], 'QUEUED');
expect(result.Status).to.equal('QUEUED');
expect(uxStub.callCount).to.equal(1);
expect(uxStub.firstCall.args[0]).to.include(
'PackageUploadRequest has been enqueued. You can query the status using\nsfdx force:package1:beta:version:create:get -i 0HD4p000000blUvGXX -u test@user.com'
);
});

it('should validate --version', async () => {
const result = await runCmd(['--packageid', '03346000000MrC0AXX', '--name', 'test', '--version', '2.3'], 'SUCCESS');
expect(result.Status).to.equal('SUCCESS');
expect(uxStub.callCount).to.equal(1);
expect(uxStub.firstCall.args[0]).to.include('Successfully uploaded package [04t4p000002BavTXXX]');
});

it('should validate --version (incorrect format SemVer)', async () => {
try {
await runCmd(['--packageid', '03346000000MrC0AXX', '--name', 'test', '--version', '2.3.3'], 'SUCCESS');
assert.fail('the above should throw an invalid version error');
} catch (e) {
expect((e as Error).message).to.include(
'Version supplied, 2.3.3, is not formatted correctly. Enter in major.minor format, for example, 3.2.'
);
}
});

it('should validate --version (incorrect format major only)', async () => {
try {
await runCmd(['--packageid', '03346000000MrC0AXX', '--name', 'test', '--version', '2'], 'SUCCESS');
assert.fail('the above should throw an invalid version error');
} catch (e) {
expect((e as Error).message).to.include(
'Version supplied, 2, is not formatted correctly. Enter in major.minor format, for example, 3.2.'
);
}
});
});
Loading

0 comments on commit 15636a0

Please sign in to comment.