diff --git a/.changeset/rare-seas-eat.md b/.changeset/rare-seas-eat.md new file mode 100644 index 00000000000..59044415fc6 --- /dev/null +++ b/.changeset/rare-seas-eat.md @@ -0,0 +1,5 @@ +--- +'@aws-amplify/backend-function': patch +--- + +Clear generated env directory before shim generation diff --git a/.changeset/seven-rabbits-poke.md b/.changeset/seven-rabbits-poke.md deleted file mode 100644 index a845151cc84..00000000000 --- a/.changeset/seven-rabbits-poke.md +++ /dev/null @@ -1,2 +0,0 @@ ---- ---- diff --git a/package-lock.json b/package-lock.json index 35127fe7aa4..016c30bf130 100644 --- a/package-lock.json +++ b/package-lock.json @@ -23296,6 +23296,7 @@ "version": "11.2.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.2.0.tgz", "integrity": "sha512-PmDi3uwK5nFuXh7XDTlVnS17xJS7vW36is2+w3xcv8SVxiB4NyATf4ctkVY5bkSjX0Y4nbvZCq1/EjtEyr9ktw==", + "dev": true, "license": "MIT", "dependencies": { "graceful-fs": "^4.2.0", @@ -23970,6 +23971,7 @@ "version": "9.0.6", "resolved": "https://registry.npmjs.org/immer/-/immer-9.0.6.tgz", "integrity": "sha512-G95ivKpy+EvVAnAab4fVa4YGYn24J1SpEktnJX7JJ45Bd7xqME/SCplFzYFmTbrkwZbQ4xJK1xMTUYBkN6pWsQ==", + "dev": true, "license": "MIT", "funding": { "type": "opencollective", @@ -30146,6 +30148,7 @@ "version": "8.3.2", "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", + "dev": true, "license": "MIT", "bin": { "uuid": "dist/bin/uuid" @@ -30929,17 +30932,17 @@ } }, "packages/ampx": { - "version": "0.2.1", + "version": "0.2.2", "license": "Apache-2.0" }, "packages/auth-construct": { "name": "@aws-amplify/auth-construct", - "version": "1.3.0", + "version": "1.3.1", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.1.0", - "@aws-amplify/backend-output-storage": "^1.1.1", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/backend-output-storage": "^1.1.2", + "@aws-amplify/plugin-types": "^1.2.2", "@aws-sdk/util-arn-parser": "^3.568.0" }, "peerDependencies": { @@ -30949,20 +30952,20 @@ }, "packages/backend": { "name": "@aws-amplify/backend", - "version": "1.2.1", + "version": "1.3.0", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/backend-auth": "^1.1.2", - "@aws-amplify/backend-data": "^1.1.3", - "@aws-amplify/backend-function": "^1.4.0", + "@aws-amplify/backend-auth": "^1.2.0", + "@aws-amplify/backend-data": "^1.1.4", + "@aws-amplify/backend-function": "^1.5.0", "@aws-amplify/backend-output-schemas": "^1.2.0", - "@aws-amplify/backend-output-storage": "^1.1.1", - "@aws-amplify/backend-secret": "^1.0.1", - "@aws-amplify/backend-storage": "^1.1.1", - "@aws-amplify/client-config": "^1.3.0", + "@aws-amplify/backend-output-storage": "^1.1.2", + "@aws-amplify/backend-secret": "^1.1.2", + "@aws-amplify/backend-storage": "^1.2.0", + "@aws-amplify/client-config": "^1.3.1", "@aws-amplify/data-schema": "^1.0.0", "@aws-amplify/platform-core": "^1.1.0", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.3.0", "@aws-sdk/client-amplify": "^3.624.0", "lodash.snakecase": "^4.1.1" }, @@ -30995,15 +30998,15 @@ }, "packages/backend-auth": { "name": "@aws-amplify/backend-auth", - "version": "1.1.4", + "version": "1.2.0", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/auth-construct": "^1.3.0", - "@aws-amplify/backend-output-storage": "^1.1.1", - "@aws-amplify/plugin-types": "^1.2.1" + "@aws-amplify/auth-construct": "^1.3.1", + "@aws-amplify/backend-output-storage": "^1.1.2", + "@aws-amplify/plugin-types": "^1.3.0" }, "devDependencies": { - "@aws-amplify/backend-platform-test-stubs": "^0.3.4", + "@aws-amplify/backend-platform-test-stubs": "^0.3.5", "@aws-amplify/platform-core": "^1.0.6" }, "peerDependencies": { @@ -31013,17 +31016,17 @@ }, "packages/backend-data": { "name": "@aws-amplify/backend-data", - "version": "1.1.3", + "version": "1.1.4", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.1.0", - "@aws-amplify/backend-output-storage": "^1.1.1", + "@aws-amplify/backend-output-storage": "^1.1.2", "@aws-amplify/data-construct": "^1.10.1", "@aws-amplify/data-schema-types": "^1.1.1", - "@aws-amplify/plugin-types": "^1.2.1" + "@aws-amplify/plugin-types": "^1.2.2" }, "devDependencies": { - "@aws-amplify/backend-platform-test-stubs": "^0.3.4", + "@aws-amplify/backend-platform-test-stubs": "^0.3.5", "@aws-amplify/data-schema": "^1.0.0", "@aws-amplify/platform-core": "^1.0.7" }, @@ -31034,11 +31037,11 @@ }, "packages/backend-deployer": { "name": "@aws-amplify/backend-deployer", - "version": "1.1.2", + "version": "1.1.4", "license": "Apache-2.0", "dependencies": { "@aws-amplify/platform-core": "^1.0.6", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "execa": "^8.0.1", "tsx": "^4.6.1" }, @@ -31049,16 +31052,16 @@ }, "packages/backend-function": { "name": "@aws-amplify/backend-function", - "version": "1.4.0", + "version": "1.5.0", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.1.0", - "@aws-amplify/backend-output-storage": "^1.1.1", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/backend-output-storage": "^1.1.2", + "@aws-amplify/plugin-types": "^1.3.0", "execa": "^8.0.1" }, "devDependencies": { - "@aws-amplify/backend-platform-test-stubs": "^0.3.4", + "@aws-amplify/backend-platform-test-stubs": "^0.3.5", "@aws-amplify/platform-core": "^1.1.0", "@aws-sdk/client-ssm": "^3.624.0", "aws-sdk": "^2.1550.0", @@ -31096,12 +31099,12 @@ }, "packages/backend-output-storage": { "name": "@aws-amplify/backend-output-storage", - "version": "1.1.1", + "version": "1.1.2", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.2.0", "@aws-amplify/platform-core": "^1.0.6", - "@aws-amplify/plugin-types": "^1.2.1" + "@aws-amplify/plugin-types": "^1.2.2" }, "peerDependencies": { "aws-cdk-lib": "^2.152.0" @@ -31109,21 +31112,21 @@ }, "packages/backend-platform-test-stubs": { "name": "@aws-amplify/backend-platform-test-stubs", - "version": "0.3.4", + "version": "0.3.5", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "aws-cdk-lib": "^2.152.0", "constructs": "^10.0.0" } }, "packages/backend-secret": { "name": "@aws-amplify/backend-secret", - "version": "1.1.1", + "version": "1.1.3", "license": "Apache-2.0", "dependencies": { "@aws-amplify/platform-core": "^1.0.5", - "@aws-amplify/plugin-types": "^1.1.1", + "@aws-amplify/plugin-types": "^1.2.2", "@aws-sdk/client-ssm": "^3.624.0" }, "devDependencies": { @@ -31132,15 +31135,15 @@ }, "packages/backend-storage": { "name": "@aws-amplify/backend-storage", - "version": "1.1.2", + "version": "1.2.0", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.2.0", - "@aws-amplify/backend-output-storage": "^1.1.1", - "@aws-amplify/plugin-types": "^1.2.1" + "@aws-amplify/backend-output-storage": "^1.1.2", + "@aws-amplify/plugin-types": "^1.3.0" }, "devDependencies": { - "@aws-amplify/backend-platform-test-stubs": "^0.3.4", + "@aws-amplify/backend-platform-test-stubs": "^0.3.5", "@aws-amplify/platform-core": "^1.0.6" }, "peerDependencies": { @@ -31150,21 +31153,21 @@ }, "packages/cli": { "name": "@aws-amplify/backend-cli", - "version": "1.2.6", + "version": "1.2.8", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/backend-deployer": "^1.1.1", + "@aws-amplify/backend-deployer": "^1.1.3", "@aws-amplify/backend-output-schemas": "^1.1.0", - "@aws-amplify/backend-secret": "^1.1.0", - "@aws-amplify/cli-core": "^1.1.2", - "@aws-amplify/client-config": "^1.2.1", - "@aws-amplify/deployed-backend-client": "^1.3.0", - "@aws-amplify/form-generator": "^1.0.1", - "@aws-amplify/model-generator": "^1.0.5", + "@aws-amplify/backend-secret": "^1.1.2", + "@aws-amplify/cli-core": "^1.1.3", + "@aws-amplify/client-config": "^1.3.1", + "@aws-amplify/deployed-backend-client": "^1.4.1", + "@aws-amplify/form-generator": "^1.0.3", + "@aws-amplify/model-generator": "^1.0.8", "@aws-amplify/platform-core": "^1.0.5", - "@aws-amplify/plugin-types": "^1.2.1", - "@aws-amplify/sandbox": "^1.2.0", - "@aws-amplify/schema-generator": "^1.2.1", + "@aws-amplify/plugin-types": "^1.3.0", + "@aws-amplify/sandbox": "^1.2.2", + "@aws-amplify/schema-generator": "^1.2.4", "@aws-sdk/client-amplify": "^3.624.0", "@aws-sdk/client-cloudformation": "^3.624.0", "@aws-sdk/client-s3": "^3.624.0", @@ -31197,7 +31200,7 @@ }, "packages/cli-core": { "name": "@aws-amplify/cli-core", - "version": "1.1.2", + "version": "1.1.3", "license": "Apache-2.0", "dependencies": { "@aws-amplify/platform-core": "^1.0.5", @@ -31304,14 +31307,14 @@ }, "packages/client-config": { "name": "@aws-amplify/client-config", - "version": "1.3.0", + "version": "1.3.2", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.2.0", - "@aws-amplify/deployed-backend-client": "^1.4.0", - "@aws-amplify/model-generator": "^1.0.5", + "@aws-amplify/deployed-backend-client": "^1.4.1", + "@aws-amplify/model-generator": "^1.0.7", "@aws-amplify/platform-core": "^1.0.7", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "zod": "^3.22.2" }, "devDependencies": { @@ -31326,12 +31329,12 @@ } }, "packages/create-amplify": { - "version": "1.0.5", + "version": "1.0.6", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/cli-core": "^1.1.1", + "@aws-amplify/cli-core": "^1.1.3", "@aws-amplify/platform-core": "^1.0.3", - "@aws-amplify/plugin-types": "^1.1.0", + "@aws-amplify/plugin-types": "^1.2.2", "execa": "^8.0.1", "kleur": "^4.1.5", "yargs": "^17.7.2" @@ -31441,12 +31444,12 @@ }, "packages/deployed-backend-client": { "name": "@aws-amplify/deployed-backend-client", - "version": "1.4.0", + "version": "1.4.1", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.2.0", "@aws-amplify/platform-core": "^1.0.5", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "zod": "^3.22.2" }, "peerDependencies": { @@ -31469,7 +31472,7 @@ }, "packages/form-generator": { "name": "@aws-amplify/form-generator", - "version": "1.0.1", + "version": "1.0.3", "license": "Apache-2.0", "dependencies": { "@aws-amplify/appsync-modelgen-plugin": "^2.11.0", @@ -31489,20 +31492,20 @@ }, "packages/integration-tests": { "name": "@aws-amplify/integration-tests", - "version": "0.5.8", + "version": "0.5.9", "license": "Apache-2.0", "devDependencies": { "@apollo/client": "^3.10.1", "@aws-amplify/ai-constructs": "^0.1.0", - "@aws-amplify/auth-construct": "^1.2.2", - "@aws-amplify/backend": "^1.2.1", + "@aws-amplify/auth-construct": "^1.3.1", + "@aws-amplify/backend": "^1.2.2", "@aws-amplify/backend-ai": "^0.1.0", - "@aws-amplify/backend-secret": "^1.0.1", - "@aws-amplify/client-config": "^1.1.3", + "@aws-amplify/backend-secret": "^1.1.2", + "@aws-amplify/client-config": "^1.3.1", "@aws-amplify/data-schema": "^1.0.0", - "@aws-amplify/deployed-backend-client": "^1.3.0", + "@aws-amplify/deployed-backend-client": "^1.4.1", "@aws-amplify/platform-core": "^1.1.0", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "@aws-sdk/client-accessanalyzer": "^3.624.0", "@aws-sdk/client-amplify": "^3.624.0", "@aws-sdk/client-bedrock-runtime": "^3.622.0", @@ -31548,15 +31551,15 @@ }, "packages/model-generator": { "name": "@aws-amplify/model-generator", - "version": "1.0.6", + "version": "1.0.8", "license": "Apache-2.0", "dependencies": { "@aws-amplify/backend-output-schemas": "^1.1.0", - "@aws-amplify/deployed-backend-client": "^1.3.0", + "@aws-amplify/deployed-backend-client": "^1.4.1", "@aws-amplify/graphql-generator": "^0.4.0", "@aws-amplify/graphql-types-generator": "^3.6.0", "@aws-amplify/platform-core": "^1.0.5", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.3.0", "@aws-sdk/client-appsync": "^3.624.0", "@aws-sdk/client-s3": "^3.624.0", "@aws-sdk/credential-providers": "^3.624.0", @@ -31602,7 +31605,7 @@ }, "packages/plugin-types": { "name": "@aws-amplify/plugin-types", - "version": "1.2.1", + "version": "1.3.0", "license": "Apache-2.0", "devDependencies": { "execa": "^5.1.1" @@ -31731,16 +31734,16 @@ }, "packages/sandbox": { "name": "@aws-amplify/sandbox", - "version": "1.2.1", + "version": "1.2.2", "license": "Apache-2.0", "dependencies": { - "@aws-amplify/backend-deployer": "^1.1.0", - "@aws-amplify/backend-secret": "^1.1.1", - "@aws-amplify/cli-core": "^1.1.2", - "@aws-amplify/client-config": "^1.1.3", - "@aws-amplify/deployed-backend-client": "^1.3.0", + "@aws-amplify/backend-deployer": "^1.1.3", + "@aws-amplify/backend-secret": "^1.1.2", + "@aws-amplify/cli-core": "^1.1.3", + "@aws-amplify/client-config": "^1.3.1", + "@aws-amplify/deployed-backend-client": "^1.4.1", "@aws-amplify/platform-core": "^1.0.6", - "@aws-amplify/plugin-types": "^1.2.1", + "@aws-amplify/plugin-types": "^1.2.2", "@aws-sdk/client-cloudformation": "^3.624.0", "@aws-sdk/client-cloudwatch-logs": "^3.624.0", "@aws-sdk/client-lambda": "^3.624.0", @@ -31764,7 +31767,7 @@ }, "packages/schema-generator": { "name": "@aws-amplify/schema-generator", - "version": "1.2.2", + "version": "1.2.4", "license": "Apache-2.0", "dependencies": { "@aws-amplify/graphql-schema-generator": "^0.9.4", diff --git a/packages/backend-function/src/factory.ts b/packages/backend-function/src/factory.ts index 46e66c15c47..574049b0d5f 100644 --- a/packages/backend-function/src/factory.ts +++ b/packages/backend-function/src/factory.ts @@ -133,6 +133,7 @@ export type FunctionProps = { */ class FunctionFactory implements ConstructFactory { private generator: ConstructContainerEntryGenerator; + /** * Create a new AmplifyFunctionFactory */ diff --git a/packages/backend-function/src/function_env_type_generator.test.ts b/packages/backend-function/src/function_env_type_generator.test.ts index d988e06fec4..19164319b4e 100644 --- a/packages/backend-function/src/function_env_type_generator.test.ts +++ b/packages/backend-function/src/function_env_type_generator.test.ts @@ -1,11 +1,15 @@ -import { describe, it, mock } from 'node:test'; +import { beforeEach, describe, it, mock } from 'node:test'; import fs from 'fs'; import fsp from 'fs/promises'; import { FunctionEnvironmentTypeGenerator } from './function_env_type_generator.js'; import assert from 'assert'; import { pathToFileURL } from 'url'; +import path from 'path'; void describe('FunctionEnvironmentTypeGenerator', () => { + beforeEach(() => { + resetFactoryCount(); + }); void it('generates a type definition file', () => { const fsOpenSyncMock = mock.method(fs, 'openSync'); const fsWriteFileSyncMock = mock.method(fs, 'writeFileSync', () => null); @@ -69,4 +73,59 @@ void describe('FunctionEnvironmentTypeGenerator', () => { await fsp.rm(targetDirectory, { recursive: true, force: true }); }); + void it('clears the generated env directory', async () => { + const fsExistsSyncMock = mock.method(fs, 'existsSync', () => true); + const fsRmSyncMock = mock.method(fs, 'rmSync', () => {}); + + const functionEnvironmentTypeGenerator = + new FunctionEnvironmentTypeGenerator('testFunction'); + + assert.equal(fsExistsSyncMock.mock.calls.length, 1); + assert.equal(fsRmSyncMock.mock.calls.length, 1); + + const functionEnvironmentTypeGenerator2 = + new FunctionEnvironmentTypeGenerator('testFunction2'); + + functionEnvironmentTypeGenerator.clearGeneratedEnvDirectory(); + functionEnvironmentTypeGenerator2.clearGeneratedEnvDirectory(); + + assert.equal(fsExistsSyncMock.mock.calls.length, 1); + assert.equal(fsRmSyncMock.mock.calls.length, 1); + + fsExistsSyncMock.mock.restore(); + fsRmSyncMock.mock.restore(); + }); + void it("don't clear the generated env directory if it doesn't exist", async () => { + const fsExistsSyncMock = mock.method(fs, 'existsSync', () => false); + const fsRmSyncMock = mock.method(fs, 'rmSync', () => {}); + + new FunctionEnvironmentTypeGenerator('testFunction'); + + assert.equal(fsExistsSyncMock.mock.calls.length, 1); + assert.equal(fsRmSyncMock.mock.calls.length, 0); + + fsExistsSyncMock.mock.restore(); + fsRmSyncMock.mock.restore(); + }); + void it('ensure correct directory is deleted', async () => { + const pathToDelete = path.join( + process.cwd(), + '.amplify', + 'generated', + 'env' + ); + const fsExistsSyncMock = mock.method(fs, 'existsSync', () => true); + const fsRmSyncMock = mock.method(fs, 'rmSync', () => {}); + + new FunctionEnvironmentTypeGenerator('testFunction'); + + assert.equal(fsExistsSyncMock.mock.calls.length, 1); + assert.equal(fsRmSyncMock.mock.calls[0].arguments[0], pathToDelete); + + fsExistsSyncMock.mock.restore(); + fsRmSyncMock.mock.restore(); + }); + const resetFactoryCount = () => { + FunctionEnvironmentTypeGenerator.isEnvDirectoryInitialized = false; + }; }); diff --git a/packages/backend-function/src/function_env_type_generator.ts b/packages/backend-function/src/function_env_type_generator.ts index ea650e26c9b..a6c5effe656 100644 --- a/packages/backend-function/src/function_env_type_generator.ts +++ b/packages/backend-function/src/function_env_type_generator.ts @@ -7,10 +7,11 @@ import { EOL } from 'os'; * Generates a typed process.env shim for environment variables */ export class FunctionEnvironmentTypeGenerator { + // Using this to ensure directory is cleared once + static isEnvDirectoryInitialized = false; private readonly header = '// This file is auto-generated by Amplify. Edits will be overwritten.'; - // The variable gets updated when the fully typed file is updated. private readonly envAssignment = 'export const env = process.env'; private typeDefFilePath: string; @@ -21,10 +22,33 @@ export class FunctionEnvironmentTypeGenerator { * Initialize typed process.env shim file name and location */ constructor(private readonly functionName: string) { - this.typeDefFilePath = `${process.cwd()}/.amplify/generated/env/${ - this.functionName - }.ts`; + this.typeDefFilePath = path.join( + process.cwd(), + '.amplify', + 'generated', + 'env', + `${this.functionName}.ts` + ); + this.clearGeneratedEnvDirectory(); } + /** + * Clear existing files and subdirectories in the generated env directory + */ + public clearGeneratedEnvDirectory = (): void => { + if (FunctionEnvironmentTypeGenerator.isEnvDirectoryInitialized) { + return; + } + const pathToDelete = path.join( + process.cwd(), + '.amplify', + 'generated', + 'env' + ); + if (fs.existsSync(pathToDelete)) { + fs.rmSync(pathToDelete, { recursive: true, force: true }); + FunctionEnvironmentTypeGenerator.isEnvDirectoryInitialized = true; + } + }; /** * Generate a typed process.env shim