diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index e2fef5f2..bd3a3b26 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -151,6 +151,7 @@ jobs: CDK_DEPLOY_REGION: 'us-east-2' GH_TOKEN: ${{ github.token }} TEST_ENVIRONMENT_NAME: ${{ steps.get_test_env_name.outputs.test_env_name }} + DASH0_AUTHORIZATION_TOKEN: ${{ secrets.DASH0_AUTHORIZATION_TOKEN }} run: | npx projen deploy --require-approval never --outputs-file ./cdk-outputs.json diff --git a/packages/otelbin-validation-image/Dockerfile b/packages/otelbin-validation-image/Dockerfile index 875c1b63..f8d19868 100644 --- a/packages/otelbin-validation-image/Dockerfile +++ b/packages/otelbin-validation-image/Dockerfile @@ -26,12 +26,20 @@ RUN /usr/app/rpm_download.sh FROM public.ecr.aws/lambda/nodejs:18 AS builder -WORKDIR /usr/app +WORKDIR /usr/app COPY package.json package.json COPY src/ src/ RUN npm install RUN npm run build +FROM golang:1.22 AS builder-extension + +RUN apt-get update && apt-get install -y zip make +RUN wget https://github.com/open-telemetry/opentelemetry-lambda/archive/refs/tags/layer-collector/0.6.0.zip +RUN unzip 0.6.0.zip +WORKDIR /go/opentelemetry-lambda-layer-collector-0.6.0/collector +RUN make package + FROM public.ecr.aws/lambda/nodejs:18 # Install useradd command needed by the OtelContrib RPM @@ -40,6 +48,7 @@ RUN yum -y install python3 python3-pip shadow-utils WORKDIR /usr/otelcol COPY --from=downloader /download/otelcol.rpm otelcol.rpm +COPY --from=builder-extension /go/opentelemetry-lambda-layer-collector-0.6.0/collector/build/extensions /opt/extensions # Install the collector's RPM package RUN rpm -i otelcol.rpm \ @@ -53,8 +62,22 @@ RUN rpm -i otelcol.rpm \ # Add the event handler COPY --from=builder /usr/app/dist /usr/app/src -COPY --from=builder /usr/app/package.json /usr/app/package.json +COPY --from=builder /usr/app/package.json /usr/app/src/package.json + +# Copy the collector config so that telemetry data can be exported. +# https://github.com/open-telemetry/opentelemetry-lambda/blob/layer-collector/0.6.0/collector/internal/collector/collector.go#L51-L54 +COPY collector.yaml /opt/collector-config/config.yaml + +# Set relevant environment variable to enable OpenTelemetry +ENV OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4328 +ENV OTEL_PROPAGATORS="tracecontext,baggage" +ENV OTEL_LAMBDA_DISABLE_AWS_CONTEXT_PROPAGATION=true +# Fix "DEBUG Recording is off, propagating context in a non-recording span" +ENV OTEL_TRACES_SAMPLER=always_on +#ENV OTEL_LOG_LEVEL=DEBUG +ENV NODE_OPTIONS="--require /usr/app/src/lambda-wrapper.js" +ENV _HANDLER="index.handler" WORKDIR /usr/app/src -CMD ["/usr/app/src/index.handler"] \ No newline at end of file +CMD ["/usr/app/src/index.handler"] diff --git a/packages/otelbin-validation-image/collector.yaml b/packages/otelbin-validation-image/collector.yaml new file mode 100644 index 00000000..a13b127b --- /dev/null +++ b/packages/otelbin-validation-image/collector.yaml @@ -0,0 +1,30 @@ +receivers: + otlp: + protocols: + grpc: + # non-standard port to avoid port conflicts with the collectors we spawn for validation + endpoint: "localhost:4327" + http: + # non-standard port to avoid port conflicts with the collectors we spawn for validation + endpoint: "localhost:4328" + +exporters: + otlp: + endpoint: ingress.eu-west-1.aws.dash0.com:4317 + headers: + Authorization: "Bearer ${DASH0_AUTHORIZATION_TOKEN}" + +service: + pipelines: + traces: + receivers: [otlp] + exporters: [otlp] + metrics: + receivers: [otlp] + exporters: [otlp] + logs: + receivers: [otlp] + exporters: [otlp] + telemetry: + metrics: + address: localhost:8888 diff --git a/packages/otelbin-validation-image/package-lock.json b/packages/otelbin-validation-image/package-lock.json index 72a16660..c85adb6e 100644 --- a/packages/otelbin-validation-image/package-lock.json +++ b/packages/otelbin-validation-image/package-lock.json @@ -10,6 +10,20 @@ "license": "Apache 2", "dependencies": { "@expo/spawn-async": "^1.7.2", + "@opentelemetry/api": "^1.7.0", + "@opentelemetry/exporter-metrics-otlp-proto": "^0.50.0", + "@opentelemetry/exporter-trace-otlp-proto": "^0.50.0", + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/instrumentation-aws-lambda": "^0.40.0", + "@opentelemetry/instrumentation-aws-sdk": "^0.40.0", + "@opentelemetry/instrumentation-dns": "^0.35.0", + "@opentelemetry/instrumentation-http": "^0.35.0", + "@opentelemetry/instrumentation-net": "^0.35.0", + "@opentelemetry/resource-detector-aws": "^1.3.4", + "@opentelemetry/resources": "^1.18.1", + "@opentelemetry/sdk-metrics": "^1.18.1", + "@opentelemetry/sdk-trace-base": "^1.18.1", + "@opentelemetry/sdk-trace-node": "^1.18.1", "aws-lambda": "^1.0.7", "js-yaml": "^4.1.0" }, @@ -1395,6 +1409,880 @@ "@jridgewell/sourcemap-codec": "^1.4.14" } }, + "node_modules/@opentelemetry/api": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.8.0.tgz", + "integrity": "sha512-I/s6F7yKUDdtMsoBWXJe8Qz40Tui5vsuKCWJEWVL+5q9sSWRzzx6v2KeNsOBEwd94j0eWkpWCH4yB6rZg9Mf0w==", + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@opentelemetry/api-logs": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.50.0.tgz", + "integrity": "sha512-JdZuKrhOYggqOpUljAq4WWNi5nB10PmgoF0y2CvedLGXd0kSawb/UBnWT8gg1ND3bHCNHStAIVT0ELlxJJRqrA==", + "dependencies": { + "@opentelemetry/api": "^1.0.0" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/context-async-hooks": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-1.24.1.tgz", + "integrity": "sha512-R5r6DO4kgEOVBxFXhXjwospLQkv+sYxwCfjvoZBe7Zm6KKXAV9kDSJhi/D1BweowdZmO+sdbENLs374gER8hpQ==", + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/core": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.23.0.tgz", + "integrity": "sha512-hdQ/a9TMzMQF/BO8Cz1juA43/L5YGtCSiKoOHmrTEf7VMDAZgy8ucpWx3eQTnQ3gBloRcWtzvcrMZABC3PTSKQ==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-http": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-http/-/exporter-metrics-otlp-http-0.50.0.tgz", + "integrity": "sha512-DMilj0pTOGxeaRPvVBil/KugvLMV5l+GzoXEWBKXYGEnfNlX+huPeMpYl+zJJBtI3Coht2KArnNOLhs2wqA3yA==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/otlp-exporter-base": "0.50.0", + "@opentelemetry/otlp-transformer": "0.50.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/sdk-metrics": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/resources": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.23.0.tgz", + "integrity": "sha512-iPRLfVfcEQynYGo7e4Di+ti+YQTAY0h5mQEUJcHlU9JOqpb4x965O6PZ+wMcwYVY63G96KtdS86YCM1BF1vQZg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/sdk-metrics": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-1.23.0.tgz", + "integrity": "sha512-4OkvW6+wST4h6LFG23rXSTf6nmTf201h9dzq7bE0z5R9ESEVLERZz6WXwE7PSgg1gdjlaznm1jLJf8GttypFDg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "lodash.merge": "^4.6.2" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-proto": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-proto/-/exporter-metrics-otlp-proto-0.50.0.tgz", + "integrity": "sha512-1kDjDgA9dF7GRp9Dd22MbY+WXXdPPiHLo4E9LWRyJG9E/hZkRy2zapOa/nWhadvG+4Ji65MRhPrZUvnqC/INww==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.50.0", + "@opentelemetry/otlp-exporter-base": "0.50.0", + "@opentelemetry/otlp-proto-exporter-base": "0.50.0", + "@opentelemetry/otlp-transformer": "0.50.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/sdk-metrics": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/resources": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.23.0.tgz", + "integrity": "sha512-iPRLfVfcEQynYGo7e4Di+ti+YQTAY0h5mQEUJcHlU9JOqpb4x965O6PZ+wMcwYVY63G96KtdS86YCM1BF1vQZg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/sdk-metrics": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-1.23.0.tgz", + "integrity": "sha512-4OkvW6+wST4h6LFG23rXSTf6nmTf201h9dzq7bE0z5R9ESEVLERZz6WXwE7PSgg1gdjlaznm1jLJf8GttypFDg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "lodash.merge": "^4.6.2" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-trace-otlp-proto": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-proto/-/exporter-trace-otlp-proto-0.50.0.tgz", + "integrity": "sha512-vavD9Ow6yOLiD+ocuS/oeciCsXNdsN41aYUrEljNaLXogvnkfMhJ+JLAhOnRSpzlVtRp7Ciw2BYGdYSebR0OsA==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/otlp-exporter-base": "0.50.0", + "@opentelemetry/otlp-proto-exporter-base": "0.50.0", + "@opentelemetry/otlp-transformer": "0.50.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/sdk-trace-base": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" + } + }, + "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/resources": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.23.0.tgz", + "integrity": "sha512-iPRLfVfcEQynYGo7e4Di+ti+YQTAY0h5mQEUJcHlU9JOqpb4x965O6PZ+wMcwYVY63G96KtdS86YCM1BF1vQZg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.23.0.tgz", + "integrity": "sha512-PzBmZM8hBomUqvCddF/5Olyyviayka44O5nDWq673np3ctnvwMOvNrsUORZjKja1zJbwEuD9niAGbnVrz3jwRQ==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/instrumentation": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.50.0.tgz", + "integrity": "sha512-bhGhbJiZKpuu7wTaSak4hyZcFPlnDeuSF/2vglze8B4w2LubcSbbOnkVTzTs5SXtzh4Xz8eRjaNnAm+u2GYufQ==", + "dependencies": { + "@opentelemetry/api-logs": "0.50.0", + "@types/shimmer": "^1.0.2", + "import-in-the-middle": "1.7.1", + "require-in-the-middle": "^7.1.1", + "semver": "^7.5.2", + "shimmer": "^1.2.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-aws-lambda": { + "version": "0.40.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-aws-lambda/-/instrumentation-aws-lambda-0.40.0.tgz", + "integrity": "sha512-DF1Ja1AQNV8K5tAW4STcI0KKuu1IDzCM1aa66UDbJwZfEMq0QedzKS7FjoIB+wV4Mk8+WJQRtzISFmjDiquxmw==", + "dependencies": { + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/propagator-aws-xray": "^1.3.1", + "@opentelemetry/resources": "^1.8.0", + "@opentelemetry/semantic-conventions": "^1.0.0", + "@types/aws-lambda": "8.10.122" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-aws-lambda/node_modules/@types/aws-lambda": { + "version": "8.10.122", + "resolved": "https://registry.npmjs.org/@types/aws-lambda/-/aws-lambda-8.10.122.tgz", + "integrity": "sha512-vBkIh9AY22kVOCEKo5CJlyCgmSWvasC+SWUxL/x/vOwRobMpI/HG1xp/Ae3AqmSiZeLUbOhW0FCD3ZjqqUxmXw==" + }, + "node_modules/@opentelemetry/instrumentation-aws-sdk": { + "version": "0.40.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-aws-sdk/-/instrumentation-aws-sdk-0.40.0.tgz", + "integrity": "sha512-USjyLBbpYIp4YPcTqcvspSmckZ/i2r/LSBkcoiIfCGNsbWyEK3mBDUTV3ULL6cuA0zGvYAabNDFZ2qm5vCvAuw==", + "dependencies": { + "@opentelemetry/core": "^1.8.0", + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/propagation-utils": "^0.30.8", + "@opentelemetry/semantic-conventions": "^1.0.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-dns": { + "version": "0.35.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-dns/-/instrumentation-dns-0.35.0.tgz", + "integrity": "sha512-ci7hIJcp8AWsJntRMt397VGYh2Isou/u8nDX/fPa9nlbIR6VssgcHTpAV6j98Q2+N3/kTPcdTs/WtLI2g8Wwgg==", + "dependencies": { + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/semantic-conventions": "^1.0.0", + "semver": "^7.5.4" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-dns/node_modules/semver": { + "version": "7.6.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.2.tgz", + "integrity": "sha512-FNAIBWCx9qcRhoHcgcJ0gvU7SN1lYU2ZXuSfl04bSC5OpvDHFyJCjdNHomPXxjQlCBU67YW64PzY7/VIEH7F2w==", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@opentelemetry/instrumentation-http": { + "version": "0.35.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-http/-/instrumentation-http-0.35.1.tgz", + "integrity": "sha512-tH92LznX5pcxpuTSb6A662IdldlMk8QTtneDN66h4nIT9ch98Gtu68GSSKjMoTR25GzH3opvPC9mX2xJamxMJw==", + "dependencies": { + "@opentelemetry/core": "1.9.1", + "@opentelemetry/instrumentation": "0.35.1", + "@opentelemetry/semantic-conventions": "1.9.1", + "semver": "^7.3.5" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/core": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.9.1.tgz", + "integrity": "sha512-6/qon6tw2I8ZaJnHAQUUn4BqhTbTNRS0WP8/bA0ynaX+Uzp/DDbd0NS0Cq6TMlh8+mrlsyqDE7mO50nmv2Yvlg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.9.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.5.0" + } + }, + "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/instrumentation": { + "version": "0.35.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.35.1.tgz", + "integrity": "sha512-EZsvXqxenbRTSNsft6LDcrT4pjAiyZOx3rkDNeqKpwZZe6GmZtsXaZZKuDkJtz9fTjOGjDHjZj9/h80Ya9iIJw==", + "dependencies": { + "require-in-the-middle": "^5.0.3", + "semver": "^7.3.2", + "shimmer": "^1.2.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.9.1.tgz", + "integrity": "sha512-oPQdbFDmZvjXk5ZDoBGXG8B4tSB/qW5vQunJWQMFUBp7Xe8O1ByPANueJ+Jzg58esEBegyyxZ7LRmfJr7kFcFg==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/instrumentation-http/node_modules/require-in-the-middle": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-5.2.0.tgz", + "integrity": "sha512-efCx3b+0Z69/LGJmm9Yvi4cqEdxnoGnxYxGxBghkkTTFeXRtTCmmhO0AnAfHz59k957uTSuy8WaHqOs8wbYUWg==", + "dependencies": { + "debug": "^4.1.1", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@opentelemetry/instrumentation-http/node_modules/semver": { + "version": "7.6.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.2.tgz", + "integrity": "sha512-FNAIBWCx9qcRhoHcgcJ0gvU7SN1lYU2ZXuSfl04bSC5OpvDHFyJCjdNHomPXxjQlCBU67YW64PzY7/VIEH7F2w==", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@opentelemetry/instrumentation-net": { + "version": "0.35.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-net/-/instrumentation-net-0.35.0.tgz", + "integrity": "sha512-L5qw1G7vwxuePpuLKxpbIg49wH0brfgVhbMaMa09YX4HM6yj1KQRRGMMFxB00NQo2u42kuv/7F7AB/lWeG0yUA==", + "dependencies": { + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/semantic-conventions": "^1.0.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@opentelemetry/instrumentation/node_modules/semver": { + "version": "7.6.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.2.tgz", + "integrity": "sha512-FNAIBWCx9qcRhoHcgcJ0gvU7SN1lYU2ZXuSfl04bSC5OpvDHFyJCjdNHomPXxjQlCBU67YW64PzY7/VIEH7F2w==", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@opentelemetry/otlp-exporter-base": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.50.0.tgz", + "integrity": "sha512-JUmjmrCmE1/fc4LjCQMqLfudgSl5OpUkzx7iA94b4jgeODM7zWxUoVXL7/CT7fWf47Cn+pmKjMvTCSESqZZ3mA==", + "dependencies": { + "@opentelemetry/core": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" + } + }, + "node_modules/@opentelemetry/otlp-proto-exporter-base": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-proto-exporter-base/-/otlp-proto-exporter-base-0.50.0.tgz", + "integrity": "sha512-hlbn3eZbhxoK79Sq1ddj1f7qcx+PzsPQC/SFpJvaWgTaqacCbqJmpzWDKfRRCAC7iGX2Hj/sgpf8vysazqyMOw==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/otlp-exporter-base": "0.50.0", + "protobufjs": "^7.2.3" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.50.0.tgz", + "integrity": "sha512-s0sl1Yfqd5q1Kjrf6DqXPWzErL+XHhrXOfejh4Vc/SMTNqC902xDsC8JQxbjuramWt/+hibfguIvi7Ns8VLolA==", + "dependencies": { + "@opentelemetry/api-logs": "0.50.0", + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/sdk-logs": "0.50.0", + "@opentelemetry/sdk-metrics": "1.23.0", + "@opentelemetry/sdk-trace-base": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/resources": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.23.0.tgz", + "integrity": "sha512-iPRLfVfcEQynYGo7e4Di+ti+YQTAY0h5mQEUJcHlU9JOqpb4x965O6PZ+wMcwYVY63G96KtdS86YCM1BF1vQZg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-metrics": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-1.23.0.tgz", + "integrity": "sha512-4OkvW6+wST4h6LFG23rXSTf6nmTf201h9dzq7bE0z5R9ESEVLERZz6WXwE7PSgg1gdjlaznm1jLJf8GttypFDg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "lodash.merge": "^4.6.2" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-trace-base": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.23.0.tgz", + "integrity": "sha512-PzBmZM8hBomUqvCddF/5Olyyviayka44O5nDWq673np3ctnvwMOvNrsUORZjKja1zJbwEuD9niAGbnVrz3jwRQ==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagation-utils": { + "version": "0.30.9", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagation-utils/-/propagation-utils-0.30.9.tgz", + "integrity": "sha512-DP2Y91zyw2uNgKLbej6c3IIjyF27sKnRK/UY/6msMIVGPIbZgtH9L0JOioN5L5kYjEkH4CDvt921SjutN7hY4A==", + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" + } + }, + "node_modules/@opentelemetry/propagator-aws-xray": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-aws-xray/-/propagator-aws-xray-1.24.1.tgz", + "integrity": "sha512-RzwoLe6QzsYGcpmxxDbbbgSpe3ncxSM4dtFHXh/rCYGjyq0nZGXKvk26mJtWZ4kQ3nuiIoqSZueIuGmt/mvOTA==", + "dependencies": { + "@opentelemetry/core": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-aws-xray/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-aws-xray/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/propagator-b3": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-b3/-/propagator-b3-1.24.1.tgz", + "integrity": "sha512-nda97ZwhpZKyUJTXqQuKzNhPMUgMLunbbGWn8kroBwegn+nh6OhtyGkrVQsQLNdVKJl0KeB5z0ZgeWszrYhwFw==", + "dependencies": { + "@opentelemetry/core": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-b3/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-b3/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/propagator-jaeger": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-jaeger/-/propagator-jaeger-1.24.1.tgz", + "integrity": "sha512-7bRBJn3FG1l195A1m+xXRHvgzAOBsfmRi9uZ5Da18oTh7BLmNDiA8+kpk51FpTsU1PCikPVpRDNPhKVB6lyzZg==", + "dependencies": { + "@opentelemetry/core": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-jaeger/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/propagator-jaeger/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/resource-detector-aws": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/@opentelemetry/resource-detector-aws/-/resource-detector-aws-1.4.2.tgz", + "integrity": "sha512-Rt4cztIz8UZZ32wRbotKPVbkRfukiMM8xfzf2C1M+Puv91Cw6kDJHAfWCqkx7FdNe0e6aF4u2lkFweE1849RCg==", + "dependencies": { + "@opentelemetry/core": "^1.0.0", + "@opentelemetry/resources": "^1.0.0", + "@opentelemetry/semantic-conventions": "^1.22.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0" + } + }, + "node_modules/@opentelemetry/resources": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.24.1.tgz", + "integrity": "sha512-cyv0MwAaPF7O86x5hk3NNgenMObeejZFLJJDVuSeSMIsknlsj3oOZzRv3qSzlwYomXsICfBeFFlxwHQte5mGXQ==", + "dependencies": { + "@opentelemetry/core": "1.24.1", + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/resources/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/resources/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/sdk-logs": { + "version": "0.50.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.50.0.tgz", + "integrity": "sha512-PeUEupBB29p9nlPNqXoa1PUWNLsZnxG0DCDj3sHqzae+8y76B/A5hvZjg03ulWdnvBLYpnJslqzylG9E0IL87g==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/resources": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.4.0 <1.9.0", + "@opentelemetry/api-logs": ">=0.39.1" + } + }, + "node_modules/@opentelemetry/sdk-logs/node_modules/@opentelemetry/resources": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-1.23.0.tgz", + "integrity": "sha512-iPRLfVfcEQynYGo7e4Di+ti+YQTAY0h5mQEUJcHlU9JOqpb4x965O6PZ+wMcwYVY63G96KtdS86YCM1BF1vQZg==", + "dependencies": { + "@opentelemetry/core": "1.23.0", + "@opentelemetry/semantic-conventions": "1.23.0" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-metrics": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-1.24.1.tgz", + "integrity": "sha512-FrAqCbbGao9iKI+Mgh+OsC9+U2YMoXnlDHe06yH7dvavCKzE3S892dGtX54+WhSFVxHR/TMRVJiK/CV93GR0TQ==", + "dependencies": { + "@opentelemetry/core": "1.24.1", + "@opentelemetry/resources": "1.24.1", + "lodash.merge": "^4.6.2" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.3.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-metrics/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-metrics/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/sdk-trace-base": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.24.1.tgz", + "integrity": "sha512-zz+N423IcySgjihl2NfjBf0qw1RWe11XIAWVrTNOSSI6dtSPJiVom2zipFB2AEEtJWpv0Iz6DY6+TjnyTV5pWg==", + "dependencies": { + "@opentelemetry/core": "1.24.1", + "@opentelemetry/resources": "1.24.1", + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-base/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-base/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/sdk-trace-node": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-1.24.1.tgz", + "integrity": "sha512-/FZX8uWaGIAwsDhqI8VvQ+qWtfMNlXjaFYGc+vmxgdRFppCSSIRwrPyIhJO1qx61okyYhoyxVEZAfoiNxrfJCg==", + "dependencies": { + "@opentelemetry/context-async-hooks": "1.24.1", + "@opentelemetry/core": "1.24.1", + "@opentelemetry/propagator-b3": "1.24.1", + "@opentelemetry/propagator-jaeger": "1.24.1", + "@opentelemetry/sdk-trace-base": "1.24.1", + "semver": "^7.5.2" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-node/node_modules/@opentelemetry/core": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.24.1.tgz", + "integrity": "sha512-wMSGfsdmibI88K9wB498zXY04yThPexo8jvwNNlm542HZB7XrrMRBbAyKJqG8qDRJwIBdBrPMi4V9ZPW/sqrcg==", + "dependencies": { + "@opentelemetry/semantic-conventions": "1.24.1" + }, + "engines": { + "node": ">=14" + }, + "peerDependencies": { + "@opentelemetry/api": ">=1.0.0 <1.9.0" + } + }, + "node_modules/@opentelemetry/sdk-trace-node/node_modules/@opentelemetry/semantic-conventions": { + "version": "1.24.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.24.1.tgz", + "integrity": "sha512-VkliWlS4/+GHLLW7J/rVBA00uXus1SWvwFvcUDxDwmFxYfg/2VI6ekwdXS28cjI8Qz2ky2BzG8OUHo+WeYIWqw==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@opentelemetry/sdk-trace-node/node_modules/semver": { + "version": "7.6.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.6.2.tgz", + "integrity": "sha512-FNAIBWCx9qcRhoHcgcJ0gvU7SN1lYU2ZXuSfl04bSC5OpvDHFyJCjdNHomPXxjQlCBU67YW64PzY7/VIEH7F2w==", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@opentelemetry/semantic-conventions": { + "version": "1.23.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.23.0.tgz", + "integrity": "sha512-MiqFvfOzfR31t8cc74CTP1OZfz7MbqpAnLCra8NqQoaHJX6ncIRTdYOQYBDQ2uFISDq0WY8Y9dDTWvsgzzBYRg==", + "engines": { + "node": ">=14" + } + }, + "node_modules/@protobufjs/aspromise": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/aspromise/-/aspromise-1.1.2.tgz", + "integrity": "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ==" + }, + "node_modules/@protobufjs/base64": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/base64/-/base64-1.1.2.tgz", + "integrity": "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==" + }, + "node_modules/@protobufjs/codegen": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@protobufjs/codegen/-/codegen-2.0.4.tgz", + "integrity": "sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg==" + }, + "node_modules/@protobufjs/eventemitter": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz", + "integrity": "sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q==" + }, + "node_modules/@protobufjs/fetch": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/fetch/-/fetch-1.1.0.tgz", + "integrity": "sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ==", + "dependencies": { + "@protobufjs/aspromise": "^1.1.1", + "@protobufjs/inquire": "^1.1.0" + } + }, + "node_modules/@protobufjs/float": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@protobufjs/float/-/float-1.0.2.tgz", + "integrity": "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ==" + }, + "node_modules/@protobufjs/inquire": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/inquire/-/inquire-1.1.0.tgz", + "integrity": "sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q==" + }, + "node_modules/@protobufjs/path": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/path/-/path-1.1.2.tgz", + "integrity": "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA==" + }, + "node_modules/@protobufjs/pool": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/pool/-/pool-1.1.0.tgz", + "integrity": "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw==" + }, + "node_modules/@protobufjs/utf8": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/utf8/-/utf8-1.1.0.tgz", + "integrity": "sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw==" + }, "node_modules/@sinclair/typebox": { "version": "0.27.8", "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.8.tgz", @@ -1519,11 +2407,15 @@ "version": "20.8.10", "resolved": "https://registry.npmjs.org/@types/node/-/node-20.8.10.tgz", "integrity": "sha512-TlgT8JntpcbmKUFzjhsyhGfP2fsiz1Mv56im6enJ905xG1DAYesxJaeSbGqQmAw8OWPdhyJGhGSQGKRNJ45u9w==", - "dev": true, "dependencies": { "undici-types": "~5.26.4" } }, + "node_modules/@types/shimmer": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/@types/shimmer/-/shimmer-1.0.5.tgz", + "integrity": "sha512-9Hp0ObzwwO57DpLFF0InUjUm/II8GmKAvzbefxQTihCb7KI6yc9yzf0nLc4mVdby5N4DRCgQM2wCup9KTieeww==" + }, "node_modules/@types/stack-utils": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-2.0.3.tgz", @@ -1545,6 +2437,25 @@ "integrity": "sha512-I4q9QU9MQv4oEOz4tAHJtNz1cwuLxn2F3xcc2iV5WdqLPpUnj30aUuxt1mAxYTG+oe8CZMV/+6rU4S4gRDzqtQ==", "dev": true }, + "node_modules/acorn": { + "version": "8.11.3", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz", + "integrity": "sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==", + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-import-assertions": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.9.0.tgz", + "integrity": "sha512-cmMwop9x+8KFhxvKrKfPYmN6/pKTYYHBqLa0DfvVZcKMJWNyWLnaqND7dx/qn66R7ewM1UX5XMaDVP5wlVTaVA==", + "peerDependencies": { + "acorn": "^8" + } + }, "node_modules/ansi-escapes": { "version": "4.3.2", "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", @@ -1983,8 +2894,7 @@ "node_modules/cjs-module-lexer": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.2.3.tgz", - "integrity": "sha512-0TNiGstbQmCFwt4akjjBg5pLRTSyj/PkWQ1ZoO2zntmg9yLqSRxwEa4iCfQLGjqhiqBfOJa7W/E8wfGrTDmlZQ==", - "dev": true + "integrity": "sha512-0TNiGstbQmCFwt4akjjBg5pLRTSyj/PkWQ1ZoO2zntmg9yLqSRxwEa4iCfQLGjqhiqBfOJa7W/E8wfGrTDmlZQ==" }, "node_modules/cliui": { "version": "8.0.1", @@ -2089,7 +2999,6 @@ "version": "4.3.4", "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", - "dev": true, "dependencies": { "ms": "2.1.2" }, @@ -2538,7 +3447,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.0.tgz", "integrity": "sha512-vUptKVTpIJhcczKBbgnS+RtcuYMB8+oNzPK2/Hp3hanz8JmpATdmmgLgSaadVREkDm+e2giHwY3ZRkyjSIDDFA==", - "dev": true, "dependencies": { "function-bind": "^1.1.2" }, @@ -2566,6 +3474,17 @@ "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.13.tgz", "integrity": "sha512-4vf7I2LYV/HaWerSo3XmlMkp5eZ83i+/CDluXi/IGTs/O1sejBNhTtnxzmRZfvOUqj7lZjqHkeTvpgSFDlWZTg==" }, + "node_modules/import-in-the-middle": { + "version": "1.7.1", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.7.1.tgz", + "integrity": "sha512-1LrZPDtW+atAxH42S6288qyDFNQ2YCty+2mxEPRtfazH6Z5QwkaBSTS2ods7hnVJioF6rkRfNoA6A/MstpFXLg==", + "dependencies": { + "acorn": "^8.8.2", + "acorn-import-assertions": "^1.9.0", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, "node_modules/import-local": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", @@ -2645,7 +3564,6 @@ "version": "2.13.1", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.13.1.tgz", "integrity": "sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw==", - "dev": true, "dependencies": { "hasown": "^2.0.0" }, @@ -3514,6 +4432,16 @@ "integrity": "sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==", "dev": true }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==" + }, + "node_modules/long": { + "version": "5.2.3", + "resolved": "https://registry.npmjs.org/long/-/long-5.2.3.tgz", + "integrity": "sha512-lcHwpNoggQTObv5apGNCTdJrO69eHOZMi4BNC+rTLER8iHAqGrUVeLh/irVIM7zTw2bOXA8T6uNPeujwOLg/2Q==" + }, "node_modules/lru-cache": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", @@ -3626,11 +4554,15 @@ "node": "*" } }, + "node_modules/module-details-from-path": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/module-details-from-path/-/module-details-from-path-1.0.3.tgz", + "integrity": "sha512-ySViT69/76t8VhE1xXHK6Ch4NcDd26gx0MzKXLO+F7NOtnqH68d9zF94nT8ZWSxXh8ELOERsnJO/sWt1xZYw5A==" + }, "node_modules/ms": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" }, "node_modules/natural-compare": { "version": "1.4.0", @@ -3793,8 +4725,7 @@ "node_modules/path-parse": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", - "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", - "dev": true + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==" }, "node_modules/picocolors": { "version": "1.0.0", @@ -3874,6 +4805,29 @@ "node": ">= 6" } }, + "node_modules/protobufjs": { + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-7.3.0.tgz", + "integrity": "sha512-YWD03n3shzV9ImZRX3ccbjqLxj7NokGN0V/ESiBV5xWqrommYHYiihuIyavq03pWSGqlyvYUFmfoMKd+1rPA/g==", + "hasInstallScript": true, + "dependencies": { + "@protobufjs/aspromise": "^1.1.2", + "@protobufjs/base64": "^1.1.2", + "@protobufjs/codegen": "^2.0.4", + "@protobufjs/eventemitter": "^1.1.0", + "@protobufjs/fetch": "^1.1.0", + "@protobufjs/float": "^1.0.2", + "@protobufjs/inquire": "^1.1.0", + "@protobufjs/path": "^1.1.2", + "@protobufjs/pool": "^1.1.0", + "@protobufjs/utf8": "^1.1.0", + "@types/node": ">=13.7.0", + "long": "^5.0.0" + }, + "engines": { + "node": ">=12.0.0" + } + }, "node_modules/punycode": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.3.2.tgz", @@ -3919,11 +4873,23 @@ "node": ">=0.10.0" } }, + "node_modules/require-in-the-middle": { + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.3.0.tgz", + "integrity": "sha512-nQFEv9gRw6SJAwWD2LrL0NmQvAcO7FBwJbwmr2ttPAacfy0xuiOjE5zt+zM4xDyuyvUaxBi/9gb2SoCyNEVJcw==", + "dependencies": { + "debug": "^4.1.1", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.1" + }, + "engines": { + "node": ">=8.6.0" + } + }, "node_modules/resolve": { "version": "1.22.8", "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.8.tgz", "integrity": "sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==", - "dev": true, "dependencies": { "is-core-module": "^2.13.0", "path-parse": "^1.0.7", @@ -3999,6 +4965,11 @@ "node": ">=8" } }, + "node_modules/shimmer": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/shimmer/-/shimmer-1.2.1.tgz", + "integrity": "sha512-sQTKC1Re/rM6XyFM6fIAGHRPVGvyXfgzIDvzoq608vM+jeyVD0Tu1E6Np0Kc2zAIFWIj963V2800iF/9LPieQw==" + }, "node_modules/signal-exit": { "version": "3.0.7", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", @@ -4141,7 +5112,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", - "dev": true, "engines": { "node": ">= 0.4" }, @@ -4304,8 +5274,7 @@ "node_modules/undici-types": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", - "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==", - "dev": true + "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==" }, "node_modules/update-browserslist-db": { "version": "1.0.13", diff --git a/packages/otelbin-validation-image/package.json b/packages/otelbin-validation-image/package.json index 7bce46b3..aa3e8a2a 100644 --- a/packages/otelbin-validation-image/package.json +++ b/packages/otelbin-validation-image/package.json @@ -1,35 +1,51 @@ { - "name": "otelbin-validation-handler", - "version": "0.0.1", - "description": "AWS Lambda handler to run validation requests", - "main": "src/index.js", - "scripts": { - "test": "jest", - "build": "esbuild src/index.ts --bundle --minify --sourcemap --platform=node --target=es2020 --outfile=dist/index.js" - }, - "repository": { - "type": "git", - "url": "git+https://github.com/dash0hq/otelbin.git" - }, - "author": "", - "license": "Apache 2", - "bugs": { - "url": "https://github.com/dash0hq/otelbin/issues" - }, - "homepage": "https://github.com/dash0hq/otelbin#readme", - "devDependencies": { - "@jest/globals": "^29.7.0", - "@types/aws-lambda": "^8.10.129", - "@types/jest": "^29.5.12", - "@types/js-yaml": "^4.0.8", - "@types/node": "^20.8.10", - "esbuild": "^0.19.8", - "jest": "^29.7.0", - "ts-jest": "^29.1.2" - }, - "dependencies": { - "@expo/spawn-async": "^1.7.2", - "aws-lambda": "^1.0.7", - "js-yaml": "^4.1.0" - } + "name": "otelbin-validation-handler", + "version": "0.0.1", + "description": "AWS Lambda handler to run validation requests against OpenTelemetry collector", + "main": "src/index.js", + "scripts": { + "test": "jest", + "build": "npm run build:app && npm run build:wrapper", + "build:app": "esbuild src/index.ts --bundle --sourcemap --platform=node --target=es2020 --outfile=dist/index.js", + "build:wrapper": "esbuild src/lambda-wrapper.ts --bundle --sourcemap --platform=node --target=es2020 --outfile=dist/lambda-wrapper.js" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/dash0hq/otelbin.git" + }, + "author": "", + "license": "Apache 2", + "bugs": { + "url": "https://github.com/dash0hq/otelbin/issues" + }, + "homepage": "https://github.com/dash0hq/otelbin#readme", + "devDependencies": { + "@jest/globals": "^29.7.0", + "@types/aws-lambda": "^8.10.129", + "@types/jest": "^29.5.12", + "@types/js-yaml": "^4.0.8", + "@types/node": "^20.8.10", + "esbuild": "^0.19.8", + "jest": "^29.7.0", + "ts-jest": "^29.1.2" + }, + "dependencies": { + "@expo/spawn-async": "^1.7.2", + "aws-lambda": "^1.0.7", + "js-yaml": "^4.1.0", + "@opentelemetry/api": "^1.7.0", + "@opentelemetry/exporter-trace-otlp-proto": "^0.50.0", + "@opentelemetry/exporter-metrics-otlp-proto": "^0.50.0", + "@opentelemetry/instrumentation": "^0.50.0", + "@opentelemetry/instrumentation-aws-lambda": "^0.40.0", + "@opentelemetry/instrumentation-aws-sdk": "^0.40.0", + "@opentelemetry/instrumentation-dns": "^0.35.0", + "@opentelemetry/instrumentation-http": "^0.35.0", + "@opentelemetry/instrumentation-net": "^0.35.0", + "@opentelemetry/resource-detector-aws": "^1.3.4", + "@opentelemetry/resources": "^1.18.1", + "@opentelemetry/sdk-metrics": "^1.18.1", + "@opentelemetry/sdk-trace-base": "^1.18.1", + "@opentelemetry/sdk-trace-node": "^1.18.1" + } } diff --git a/packages/otelbin-validation-image/src/index.test.ts b/packages/otelbin-validation-image/src/index.test.ts index 3b05c598..424a5edd 100644 --- a/packages/otelbin-validation-image/src/index.test.ts +++ b/packages/otelbin-validation-image/src/index.test.ts @@ -1,4 +1,4 @@ -import { extractErrorMessage, extractErrorPath } from "./index"; +const {extractErrorPath, extractErrorMessage} = require("./index"); describe("extractErrorMessage", () => { it("must extract error message for OTel collector core/contrib when config parsing fails", () => { diff --git a/packages/otelbin-validation-image/src/index.ts b/packages/otelbin-validation-image/src/index.ts index 7e34507c..055ed908 100644 --- a/packages/otelbin-validation-image/src/index.ts +++ b/packages/otelbin-validation-image/src/index.ts @@ -1,8 +1,9 @@ -import { realpath, writeFile } from "fs/promises"; -import { spawn } from "child_process"; -import spawnAsync from "@expo/spawn-async"; -import { APIGatewayEvent, APIGatewayProxyResult } from "aws-lambda"; -import * as yaml from "js-yaml"; +import type { APIGatewayEvent, APIGatewayProxyResult } from "aws-lambda"; + +const { realpath, writeFile } = require("fs/promises"); +const { spawn } = require("child_process"); +const spawnAsync = require("@expo/spawn-async"); +const yaml = require("js-yaml"); interface SpawnError extends Error { pid: number; @@ -23,7 +24,102 @@ interface Env { const distroName = process.env.DISTRO_NAME; -export const validateAdot = async (otelcolRealPath: string, configPath: string, env: Env): Promise => { +/** + * Using CommonJS export to allow for AWS lambda layer to work as per the + * documentation + * + * > For TypeScript users, if you are using esbuild (either directly or through + * > tools such as the AWS CDK), you must export your handler function through + * > module.exports rather than with the export keyword! The AWS mananaged layer + * > for ADOT JavaScript needs to hot-patch your handler at runtime, but can't + * > because esbuild makes your handler immutable when using the export keyword. + * > Source: https://aws-otel.github.io/docs/getting-started/lambda/lambda-js + */ +exports.handler = async (event: APIGatewayEvent): Promise => { + let body = event.body!; + + if (event.isBase64Encoded) { + let buff = Buffer.from(body, "base64"); + body = buff.toString("ascii"); + } + + const validationPayload = JSON.parse(body) as ValidationPayload; + const config = validationPayload.config; + const env = validationPayload.env; + + if ( + !validationPayload || // Empty event + !config || // Empty configuration string + !config?.trim().length || // Blank configuration string (only whitespaces) + !Object.keys(yaml.load(config) as Object).length // Empty YAML + ) { + return { + statusCode: 200, + body: JSON.stringify({ + message: "The provided configuration is invalid", + error: "the provided configuration is empty" + }) + }; + } + + try { + const configPath = "/tmp/config.yaml"; + + await writeFile(configPath, config!, { + flag: "w+" + }); + + // Resolve real path (the collector binary is likely symlinked) + const otelcolRealPath = await realpath("/usr/bin/otelcol"); + + switch (distroName) { + case "adot": + await exports.validateAdot(otelcolRealPath, configPath, env); + break; + default: + await exports.validateOtelCol(otelcolRealPath, configPath, env); + } + + return { + statusCode: 200, + body: JSON.stringify({ + message: "Configuration is valid" + }) + }; + } catch (err) { + console.error(err); // should contain code (exit code) and signal (that caused the termination). + + const spawnErr = err as SpawnError; + + const status = spawnErr.status; + const stderr = spawnErr.stderr || ""; + const stdout = spawnErr.stdout || ""; + + if (isCollectorValidationFailure(stderr)) { + const error = exports.extractErrorMessage(stderr); + const path = exports.extractErrorPath(error); + + return { + statusCode: 200, + // Unfortunately the collector returns one validation error at the time + body: JSON.stringify({ + path, + message: "The provided configuration is invalid", + error + }) + }; + } + + return { + statusCode: 500, + body: JSON.stringify({ + message: `Error occurred while validating the configuration:\nstatus: ${status}\nstdout: ${stdout}\nstderr: ${stderr}\nerror: ${err}` + }) + }; + } +}; + +exports.validateAdot = async (otelcolRealPath: string, configPath: string, env: Env): Promise => { /* * ADOT does not support the `validate` subcommand * (see https://github.com/aws-observability/aws-otel-collector/issues/2391), @@ -94,7 +190,7 @@ export const validateAdot = async (otelcolRealPath: string, configPath: string, }); }; -export const validateOtelCol = async (otelcolRealPath: string, configPath: string, env: Env): Promise => { +exports.validateOtelCol = async (otelcolRealPath: string, configPath: string, env: Env): Promise => { /* * Node.js spawn is unreliable in terms of collecting stdout and stderr through the spawn call * (see https://github.com/nodejs/node/issues/19218). Getting a shell around the otelcol binary @@ -108,90 +204,6 @@ export const validateOtelCol = async (otelcolRealPath: string, configPath: strin }); }; -export const handler = async (event: APIGatewayEvent): Promise => { - let body = event.body!; - - if (event.isBase64Encoded) { - let buff = Buffer.from(body, "base64"); - body = buff.toString("ascii"); - } - - const validationPayload = JSON.parse(body) as ValidationPayload; - const config = validationPayload.config; - const env = validationPayload.env; - - if ( - !validationPayload || // Empty event - !config || // Empty configuration string - !config?.trim().length || // Blank configuration string (only whitespaces) - !Object.keys(yaml.load(config) as Object).length // Empty YAML - ) { - return { - statusCode: 200, - body: JSON.stringify({ - message: "The provided configuration is invalid", - error: "the provided configuration is empty" - }) - }; - } - - try { - const configPath = "/tmp/config.yaml"; - - await writeFile(configPath, config!, { - flag: "w+" - }); - - // Resolve real path (the collector binary is likely symlinked) - const otelcolRealPath = await realpath("/usr/bin/otelcol"); - - switch (distroName) { - case "adot": - await validateAdot(otelcolRealPath, configPath, env); - break; - default: - await validateOtelCol(otelcolRealPath, configPath, env); - } - - return { - statusCode: 200, - body: JSON.stringify({ - message: "Configuration is valid" - }) - }; - } catch (err) { - console.error(err); // should contain code (exit code) and signal (that caused the termination). - - const spawnErr = err as SpawnError; - - const status = spawnErr.status; - const stderr = spawnErr.stderr || ""; - const stdout = spawnErr.stdout || ""; - - if (isCollectorValidationFailure(stderr)) { - const error = extractErrorMessage(stderr); - const path = extractErrorPath(error); - - return { - statusCode: 200, - // Unfortunately the collector returns one validation error at the time - body: JSON.stringify({ - path, - message: "The provided configuration is invalid", - error - }) - }; - } - - return { - statusCode: 500, - body: JSON.stringify({ - message: `Error occurred while validating the configuration:\nstatus: ${status}\nstdout: ${stdout}\nstderr: ${stderr}\nerror: ${err}` - }) - }; - } -}; - const defaultErrorPrefix = "Error: "; const adotInvalidConfigPrefix = "Error: invalid configuration: "; @@ -201,7 +213,7 @@ function isCollectorValidationFailure(error: string): boolean { const parsingErrorHint = 'failed to get config:'; -export function extractErrorMessage(error: string): string { +exports.extractErrorMessage = function extractErrorMessage(error: string): string { let errorMessage: string; if (error.includes(parsingErrorHint)) { errorMessage = extractParsingErrorMessage(error); @@ -241,6 +253,6 @@ function extractValidationErrorMessage(error: string): string { [0]; } -export function extractErrorPath(errorMessage: string): string[] { +exports.extractErrorPath = function extractErrorPath(errorMessage: string): string[] { return errorMessage.match(/^((?:[\w/]+(?:::)?)+):[^:]/)?.[1].split("::"); } diff --git a/packages/otelbin-validation-image/src/lambda-wrapper.ts b/packages/otelbin-validation-image/src/lambda-wrapper.ts new file mode 100644 index 00000000..a0c80ddd --- /dev/null +++ b/packages/otelbin-validation-image/src/lambda-wrapper.ts @@ -0,0 +1,94 @@ +// This code is a 99% copy of the official OpenTelemetry Lambda wrapper for Node.js. +// https://github.com/open-telemetry/opentelemetry-lambda/blob/fefd74405214790644fe262b0f5a8a636c029184/nodejs/packages/layer/src/wrapper.ts +// +// Unfortunately, we couldn't use it as a dependency, because it is not published to npm. +// +// Changes from original: +// - removed ability to overwrite config sections via globals +// - removed some default instrumentations + +const { NodeTracerConfig, NodeTracerProvider } = require("@opentelemetry/sdk-trace-node"); +const { + BatchSpanProcessor, + ConsoleSpanExporter, + SDKRegistrationConfig, + SimpleSpanProcessor +} = require("@opentelemetry/sdk-trace-base"); +const { registerInstrumentations } = require("@opentelemetry/instrumentation"); +const { awsLambdaDetector } = require("@opentelemetry/resource-detector-aws"); +const { detectResourcesSync, envDetector, processDetector } = require("@opentelemetry/resources"); +const { AwsInstrumentation } = require("@opentelemetry/instrumentation-aws-sdk"); +const { + AwsLambdaInstrumentation, +} = require("@opentelemetry/instrumentation-aws-lambda"); +const { diag, DiagConsoleLogger, DiagLogLevel } = require("@opentelemetry/api"); +const { getEnv } = require("@opentelemetry/core"); +const { OTLPTraceExporter } = require("@opentelemetry/exporter-trace-otlp-proto"); +const { MeterProvider, MeterProviderOptions } = require("@opentelemetry/sdk-metrics"); + +function defaultConfigureInstrumentations() { + // Use require statements for instrumentation to avoid having to have transitive dependencies on all the typescript + // definitions. + const { DnsInstrumentation } = require("@opentelemetry/instrumentation-dns"); + const { HttpInstrumentation } = require("@opentelemetry/instrumentation-http"); + const { NetInstrumentation } = require("@opentelemetry/instrumentation-net"); + return [new DnsInstrumentation(), + new HttpInstrumentation(), + new NetInstrumentation() + ]; +} + +console.log("Registering OpenTelemetry"); + +const instrumentations = [ + new AwsInstrumentation({ + suppressInternalInstrumentation: true + }), + new AwsLambdaInstrumentation(defaultConfigureInstrumentations()) +]; + +// configure lambda logging +const logLevel = getEnv().OTEL_LOG_LEVEL; +diag.setLogger(new DiagConsoleLogger(), logLevel); + +// Register instrumentations synchronously to ensure code is patched even before provider is ready. +registerInstrumentations({ + instrumentations +}); + +async function initializeProvider() { + const resource = detectResourcesSync({ + detectors: [awsLambdaDetector, envDetector, processDetector] + }); + + let config: typeof NodeTracerConfig = { + resource + }; + + const tracerProvider = new NodeTracerProvider(config); + tracerProvider.addSpanProcessor( + new BatchSpanProcessor(new OTLPTraceExporter()) + ); + // logging for debug + if (logLevel===DiagLogLevel.DEBUG) { + tracerProvider.addSpanProcessor(new SimpleSpanProcessor(new ConsoleSpanExporter())); + } + + let sdkRegistrationConfig: typeof SDKRegistrationConfig = {}; + tracerProvider.register(sdkRegistrationConfig); + + // Configure default meter provider (doesn't export metrics) + let meterConfig: typeof MeterProviderOptions = { + resource + }; + + const meterProvider = new MeterProvider(meterConfig); + // Re-register instrumentation with initialized provider. Patched code will see the update. + registerInstrumentations({ + instrumentations, + tracerProvider, + meterProvider + }); +} + +initializeProvider(); diff --git a/packages/otelbin-validation/src/main.ts b/packages/otelbin-validation/src/main.ts index 46a73e17..42f0894e 100644 --- a/packages/otelbin-validation/src/main.ts +++ b/packages/otelbin-validation/src/main.ts @@ -6,7 +6,7 @@ import { Platform } from 'aws-cdk-lib/aws-ecr-assets'; import { PolicyStatement, Role, ServicePrincipal } from 'aws-cdk-lib/aws-iam'; import { Architecture, DockerImageCode, DockerImageFunction } from 'aws-cdk-lib/aws-lambda'; import { RetentionDays } from 'aws-cdk-lib/aws-logs'; -import { Bucket, BlockPublicAccess } from 'aws-cdk-lib/aws-s3'; +import { BlockPublicAccess, Bucket } from 'aws-cdk-lib/aws-s3'; import { BucketDeployment, Source } from 'aws-cdk-lib/aws-s3-deployment'; import { Construct } from 'constructs'; @@ -30,6 +30,7 @@ export interface Release { export interface OTelBinValidationStackProps extends StackProps { testEnvironmentName: string; githubToken: string; + dash0AuthorizationToken?: string; } export class OTelBinValidationStack extends Stack { @@ -131,7 +132,7 @@ export class OTelBinValidationStack extends Stack { const supportedDistributions = JSON.parse( (readFileSync(join(__dirname, 'assets', 'supported-distributions.json'))).toString(), - ) as Distributions; + ) as Distributions; for (let [distributionName, distribution] of Object.entries(supportedDistributions)) { const distributionResource = validation.addResource(distributionName); @@ -152,6 +153,7 @@ export class OTelBinValidationStack extends Stack { }), environment: { DISTRO_NAME: distributionName, + DASH0_AUTHORIZATION_TOKEN: props.dash0AuthorizationToken || '', }, /* * The default 128 cause the OtelCol process to swap a lot, and that increased @@ -201,6 +203,7 @@ const env = { region: process.env.CDK_DEFAULT_REGION, testEnvironmentName, githubToken: process.env.GH_TOKEN, + dash0AuthorizationToken: process.env.DASH0_AUTHORIZATION_TOKEN, }; const app = new App();