Skip to content

Commit 6ebcb0d

Browse files
authored
fix: Amplify test fails when CLI is installed from Verdaccio (#55)
The Amplify tests (used to) work like this: - `npm create amplify`, which runs `npx create-amplify` - Update the `package.json` to point to the correct CLI version - `npm install` and run the Amplify CLI However, during the first step (`npx create-amplify`) the Amplify CLI already picks a baked-in CLI version (let's say `[email protected]`) and `npm install`s it, before we have had a time to hack the `package.json` file. This works fine if `2.1002.0` is available to install, but in the case where we have an isolated run with the candidate packages in Verdaccio, only the release candidate is available which will have a version like `2.1002.999`, and the first step of this test fails. What we do instead is download the installer and change the package version it is about to install by editing one of its data files, `default_packages.json`.
1 parent e14424f commit 6ebcb0d

File tree

1 file changed

+62
-7
lines changed

1 file changed

+62
-7
lines changed

packages/@aws-cdk-testing/cli-integ/tests/tool-integrations/amplify.integtest.ts

+62-7
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,24 @@ const TIMEOUT = 1800_000;
88
integTest('amplify integration', withToolContext(async (context) => {
99
const shell = ShellHelper.fromContext(context);
1010

11-
await shell.shell(['npm', 'create', '-y', 'amplify@latest']);
12-
await shell.shell(['npx', 'ampx', 'configure', 'telemetry', 'disable']);
11+
////////////////////////////////////////////////////////////////////////
12+
// Make sure that create-amplify installs the right versions of the CLI and framework
13+
//
1314

15+
// Install `create-amplify` without running it, then hack the json file with the
16+
// package versions in it before we execute.
17+
await shell.shell(['npm', 'init', '-y']);
18+
await shell.shell(['npm', 'install', '--save-dev', 'create-amplify@latest']);
1419
// This will create 'package.json' implicating a certain version of the CDK
1520
await updateCdkDependency(context, context.packages.requestedCliVersion(), context.packages.requestedFrameworkVersion());
16-
await shell.shell(['npm', 'install']);
21+
22+
////////////////////////////////////////////////////////////////////////
23+
// Run the `npm create` workflow
24+
//
25+
26+
// I tested to confirm that this will use the locally installed `create-amplify`
27+
await shell.shell(['npm', 'create', '-y', 'amplify']);
28+
await shell.shell(['npx', 'ampx', 'configure', 'telemetry', 'disable']);
1729

1830
await shell.shell(['npx', 'ampx', 'sandbox', '--once'], {
1931
modEnv: {
@@ -35,9 +47,52 @@ integTest('amplify integration', withToolContext(async (context) => {
3547
}), TIMEOUT);
3648

3749
async function updateCdkDependency(context: TemporaryDirectoryContext, cliVersion: string, libVersion: string) {
38-
const filename = path.join(context.integTestDir, 'package.json');
39-
const pj = JSON.parse(await fs.readFile(filename, { encoding: 'utf-8' }));
40-
pj.devDependencies['aws-cdk'] = cliVersion;
41-
pj.devDependencies['aws-cdk-lib'] = libVersion;
50+
const filename = path.join(context.integTestDir, 'node_modules', 'create-amplify', 'lib', 'default_packages.json');
51+
const pj: unknown = JSON.parse(await fs.readFile(filename, { encoding: 'utf-8' }));
52+
53+
// Be extra paranoid about the types here, since we don't fully control them
54+
assertIsObject(pj);
55+
assertIsStringArray(pj.defaultDevPackages);
56+
57+
replacePackageVersionIn('aws-cdk', cliVersion, pj.defaultDevPackages);
58+
replacePackageVersionIn('aws-cdk-lib', libVersion, pj.defaultDevPackages);
59+
4260
await fs.writeFile(filename, JSON.stringify(pj, undefined, 2), { encoding: 'utf-8' });
4361
}
62+
63+
/**
64+
* Mutably update the given string array, replacing the version of packages with the given name
65+
*
66+
* We assume the list of packages is a string array of the form
67+
*
68+
* ```
69+
* ["package@version", "package@version", ...]
70+
* ```
71+
*
72+
* It's a failure if we don't find an entry to update.
73+
*/
74+
function replacePackageVersionIn(packName: string, version: string, xs: string[]) {
75+
let didUpdate = false;
76+
for (let i = 0; i < xs.length; i++) {
77+
if (xs[i].startsWith(`${packName}@`)) {
78+
xs[i] = `${packName}@${version}`;
79+
didUpdate = true;
80+
}
81+
}
82+
83+
if (!didUpdate) {
84+
throw new Error(`Did not find a package version to update for ${packName} in ${JSON.stringify(xs)}`);
85+
}
86+
}
87+
88+
function assertIsObject(xs: unknown): asserts xs is Record<string, unknown> {
89+
if (typeof xs !== 'object' || xs === null) {
90+
throw new Error(`Expected object, got ${JSON.stringify(xs)}`);
91+
}
92+
}
93+
94+
function assertIsStringArray(xs: unknown): asserts xs is string[] {
95+
if (!Array.isArray(xs) || xs.length === 0 || typeof xs[0] !== 'string') {
96+
throw new Error(`Expected list of strings, got ${JSON.stringify(xs)}`);
97+
}
98+
}

0 commit comments

Comments
 (0)