Skip to content
Draft
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
2 changes: 2 additions & 0 deletions .github/workflows/integration-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ jobs:
GITHUB_EVENT_NAME: ${{ github.event_name }}
GITHUB_EVENT_NUMBER: ${{ github.event.number }}
AWS_ACCOUNT_ID: ${{ secrets.AWS_ACCOUNT_ID }}
CAPACITY_PROVIDER_ARN: ${{ secrets.CAPACITY_PROVIDER_ARN }}
run: node .github/workflows/scripts/integration-test/integration-test.js --deploy-only --runtime ${{ inputs.node-version }}

jest-integration-test:
Expand Down Expand Up @@ -95,5 +96,6 @@ jobs:
LAMBDA_ENDPOINT: ${{ secrets.LAMBDA_ENDPOINT }}
GITHUB_EVENT_NAME: ${{ github.event_name }}
GITHUB_EVENT_NUMBER: ${{ github.event.number }}
CAPACITY_PROVIDER_ARN: ${{ secrets.CAPACITY_PROVIDER_ARN }}
run: |
node .github/workflows/scripts/integration-test/integration-test.js --test-only --runtime ${{ inputs.node-version }}
77 changes: 44 additions & 33 deletions .github/workflows/scripts/integration-test/integration-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,14 @@ import {
ResourceNotFoundException,
} from "@aws-sdk/client-lambda";

import dotenv from "dotenv";
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);

dotenv.config({
path: join(__dirname, "../../../../.env"),
});

// Colors for output
const COLORS = {
RED: "\x1b[0;31m",
Expand All @@ -33,9 +41,6 @@ const log = {
console.error(`${COLORS.RED}[ERROR]${COLORS.NC} ${msg}`),
};

const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);

// Configuration
const CONFIG = {
AWS_REGION: process.env.AWS_REGION || "us-east-1",
Expand All @@ -62,20 +67,17 @@ class IntegrationTestRunner {
this.cleanupOnExit = options.cleanupOnExit !== false;
this.runtime = options.runtime;
this.isGitHubActions = !!process.env.GITHUB_ACTIONS;
/** @type {Record<string, string> | undefined} */
/** @type {Record<string, {functionName: string, qualifier: string}> | undefined} */
this.functionNameMap = undefined;
/** @type {import('@aws-sdk/client-lambda').LambdaClient | null} */
this.lambdaClient = null;

// Set up cleanup handler
if (this.cleanupOnExit) {
process.on("exit", () => this.cleanup());
process.on("SIGINT", () => {
this.cleanup();
process.exit(130);
});
process.on("SIGTERM", () => {
this.cleanup();
process.exit(143);
});
}
Expand Down Expand Up @@ -140,7 +142,7 @@ class IntegrationTestRunner {
}

const examples = this.getIntegrationExamples();
/** @type {Record<string, string>} */
/** @type {Record<string, {functionName: string, qualifier: string}>} */
const functionNameMap = {};

// Get runtime suffix from argument or environment variable
Expand Down Expand Up @@ -173,15 +175,23 @@ class IntegrationTestRunner {
}

const handlerFile = exampleHandler.replace(/\.handler$/, "");
functionNameMap[handlerFile] = functionName;
functionNameMap[handlerFile] = {
functionName,
qualifier: example.capacityProviderConfig
? "$LATEST.PUBLISHED"
: "$LATEST",
};
}

this.functionNameMap = functionNameMap;
return functionNameMap;
}

// Deploy Lambda functions
async deployFunctions() {
/**
* Deploy Lambda functions
* @param {string | undefined} testPattern
*/
async deployFunctions(testPattern) {
log.info("Deploying Lambda functions...");

if (!process.env.AWS_ACCOUNT_ID) {
Expand All @@ -198,27 +208,28 @@ class IntegrationTestRunner {

// Extract handler file name from catalog
const handlerFile = exampleHandler.replace(/\.handler$/, "");
const functionName = functionNameMap[handlerFile];
const { functionName } = functionNameMap[handlerFile];

log.info(`Deploying function: ${functionName} (handler: ${handlerFile})`);
if (!testPattern || handlerFile.includes(testPattern)) {
log.info(
`Deploying function: ${functionName} (handler: ${handlerFile})`,
);

// Package the function
this.execCommand(`npm run package -- "${handlerFile}"`, {
cwd: examplesDir,
});
// Package the function
this.execCommand(`npm run package -- "${handlerFile}"`, {
cwd: examplesDir,
});

// Deploy using npm script with runtime parameter
const deployCommand = `npm run deploy -- "${handlerFile}" '${functionName}' --runtime ${this.runtime}`;
// Deploy using npm script with runtime parameter
const deployCommand = `npm run deploy -- "${handlerFile}" '${functionName}' --runtime ${this.runtime}`;

this.execCommand(deployCommand, {
cwd: examplesDir,
});
log.success(`Deployed function: ${functionName}`);
this.execCommand(deployCommand, {
cwd: examplesDir,
});
log.success(`Deployed function: ${functionName}`);
}
}

log.info("Function name map:");
console.log(JSON.stringify(functionNameMap, null, 2));

if (this.isGitHubActions) {
if (!process.env.GITHUB_OUTPUT) {
throw new Error("Could not find GITHUB_OUTPUT environment variable");
Expand All @@ -239,9 +250,11 @@ class IntegrationTestRunner {
const examplesDir = CONFIG.EXAMPLES_PACKAGE_PATH;

const functionsWithQualifier = Object.fromEntries(
Object.entries(this.getFunctionNameMap()).map(([key, value]) => {
return [key, `${value}:$LATEST`];
}),
Object.entries(this.getFunctionNameMap()).map(
([key, { functionName, qualifier }]) => {
return [key, `${functionName}:${qualifier}`];
},
),
);

// Set additional environment variables
Expand All @@ -250,8 +263,6 @@ class IntegrationTestRunner {
LAMBDA_ENDPOINT: CONFIG.LAMBDA_ENDPOINT,
};

log.info("Running Jest integration tests with function map:");
console.log(JSON.stringify(functionsWithQualifier, null, 2));
log.info(`Lambda Endpoint: ${CONFIG.LAMBDA_ENDPOINT}`);

// Build test command with optional pattern
Expand Down Expand Up @@ -282,7 +293,7 @@ class IntegrationTestRunner {
// Initialize Lambda client for cleanup
const lambdaClient = this.initializeLambdaClient();

for (const functionName of Object.values(functionNameMap)) {
for (const { functionName } of Object.values(functionNameMap)) {
log.info(`Deleting function: ${functionName}`);

const deleteCommand = new DeleteFunctionCommand({
Expand Down Expand Up @@ -329,7 +340,7 @@ class IntegrationTestRunner {
}

if (!testOnly) {
await this.deployFunctions();
await this.deployFunctions(testPattern);
}

if (!deployOnly) {
Expand Down
12 changes: 7 additions & 5 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@
"@typescript-eslint/parser": "^8.44.0",
"argparse": "^2.0.1",
"concurrently": "^9.2.1",
"dotenv": "^17.2.3",
"eslint": "^9.29.0",
"eslint-config-prettier": "^10.1.5",
"eslint-plugin-jest": "^29.0.1",
Expand Down
4 changes: 2 additions & 2 deletions packages/aws-durable-execution-sdk-js-examples/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,7 @@
"@aws-sdk/client-dynamodb": "^3.943.0",
"@aws-sdk/client-lambda": "^3.943.0",
"@aws/durable-execution-sdk-js": "*",
"@aws/durable-execution-sdk-js-testing": "*",
"dotenv": "^17.2.3"
"@aws/durable-execution-sdk-js-testing": "*"
},
"devDependencies": {
"@aws/durable-execution-sdk-js-eslint-plugin": "*",
Expand All @@ -64,6 +63,7 @@
"@types/js-yaml": "^4.0.9",
"@types/node": "^22.13.5",
"argparse": "^2.0.1",
"dotenv": "^17.2.3",
"eslint": "^9.23.0",
"jest": "^30.2.0",
"js-yaml": "^4.1.0",
Expand Down
Loading
Loading