Skip to content

Commit ed3d12f

Browse files
authored
test(e2e): Add e2e test for AWS lambda in ESM mode (#12833)
Add an E2E test app that simulates running an AWS lambda function in ESM mode. At the same time, this test app represents the state of how to manually use the `@sentry/aws-serverless` SDK for ESM-based lambda functions.
1 parent 339f25e commit ed3d12f

File tree

13 files changed

+216
-57
lines changed

13 files changed

+216
-57
lines changed

.github/workflows/build.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -995,6 +995,7 @@ jobs:
995995
'angular-17',
996996
'angular-18',
997997
'aws-lambda-layer-cjs',
998+
'aws-serverless-esm',
998999
'node-express',
9991000
'create-react-app',
10001001
'create-next-app',

dev-packages/e2e-tests/package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,8 @@
2323
"esbuild": "0.20.0",
2424
"glob": "8.0.3",
2525
"ts-node": "10.9.1",
26-
"yaml": "2.2.2"
26+
"yaml": "2.2.2",
27+
"rimraf": "^5.0.0"
2728
},
2829
"volta": {
2930
"extends": "../../package.json",
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
@sentry:registry=http://127.0.0.1:4873
2+
@sentry-internal:registry=http://127.0.0.1:4873
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
{
2+
"name": "node-express-app",
3+
"version": "1.0.0",
4+
"private": true,
5+
"scripts": {
6+
"start": "node src/run.mjs",
7+
"test": "playwright test",
8+
"clean": "npx rimraf node_modules pnpm-lock.yaml",
9+
"test:build": "pnpm install",
10+
"test:assert": "pnpm test"
11+
},
12+
"dependencies": {
13+
"@sentry/aws-serverless": "* || latest"
14+
},
15+
"devDependencies": {
16+
"@sentry-internal/test-utils": "link:../../../test-utils",
17+
"@playwright/test": "^1.41.1",
18+
"wait-port": "1.0.4"
19+
},
20+
"volta": {
21+
"extends": "../../package.json"
22+
}
23+
}
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import { getPlaywrightConfig } from '@sentry-internal/test-utils';
2+
3+
// Fix urls not resolving to localhost on Node v17+
4+
// See: https://github.com/axios/axios/issues/3821#issuecomment-1413727575
5+
import { setDefaultResultOrder } from 'dns';
6+
setDefaultResultOrder('ipv4first');
7+
8+
const eventProxyPort = 3031;
9+
10+
/**
11+
* See https://playwright.dev/docs/test-configuration.
12+
*/
13+
const config = getPlaywrightConfig(
14+
{ startCommand: '' },
15+
{
16+
/* Run your local dev server before starting the tests */
17+
webServer: [
18+
{
19+
command: `node start-event-proxy.mjs && pnpm wait-port ${eventProxyPort}`,
20+
port: eventProxyPort,
21+
stdout: 'pipe',
22+
},
23+
],
24+
},
25+
);
26+
27+
export default config;
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import * as http from 'node:http';
2+
import * as Sentry from '@sentry/aws-serverless';
3+
4+
const handler = Sentry.wrapHandler(async () => {
5+
await new Promise(resolve => {
6+
const req = http.request(
7+
{
8+
host: 'example.com',
9+
},
10+
res => {
11+
res.on('data', d => {
12+
process.stdout.write(d);
13+
});
14+
15+
res.on('end', () => {
16+
resolve();
17+
});
18+
},
19+
);
20+
req.end();
21+
});
22+
23+
Sentry.startSpan({ name: 'manual-span', op: 'manual' }, () => {});
24+
});
25+
26+
export { handler };
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"//": "This is a mock package.json file which is usually created by AWS when deploying the lambda. OTEL instrumentation tries to read this file to get the lambda version",
3+
"name": "lambda",
4+
"version": "1.0.0"
5+
}
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import { handler } from './lambda-function.mjs';
2+
3+
// Simulate minimal event and context objects being passed to the handler by the AWS runtime
4+
const event = {};
5+
const context = {
6+
invokedFunctionArn: 'arn:aws:lambda:us-east-1:123453789012:function:my-lambda',
7+
functionName: 'my-lambda',
8+
};
9+
10+
await handler(event, context);
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
import child_process from 'child_process';
2+
3+
child_process.execSync('node ./src/run-lambda.mjs', {
4+
stdio: 'inherit',
5+
env: {
6+
...process.env,
7+
// On AWS, LAMBDA_TASK_ROOT is usually /var/task but for testing, we set it to the CWD to correctly apply our handler
8+
LAMBDA_TASK_ROOT: process.cwd(),
9+
_HANDLER: 'src/lambda-function.handler',
10+
11+
NODE_OPTIONS: '--import @sentry/aws-serverless/awslambda-auto',
12+
SENTRY_DSN: 'http://public@localhost:3031/1337',
13+
SENTRY_TRACES_SAMPLE_RATE: '1.0',
14+
},
15+
cwd: process.cwd(),
16+
});
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
import { startEventProxyServer } from '@sentry-internal/test-utils';
2+
3+
startEventProxyServer({
4+
port: 3031,
5+
proxyServerName: 'aws-serverless-esm',
6+
forwardToSentry: false,
7+
});

0 commit comments

Comments
 (0)