UNPKG

@aws/aws-distro-opentelemetry-node-autoinstrumentation

Version:

This package provides Amazon Web Services distribution of the OpenTelemetry Node Instrumentation, which allows for auto-instrumentation of NodeJS applications.

136 lines 5.95 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.OTLPAwsBaseExporter = void 0; // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 const otlp_exporter_base_1 = require("@opentelemetry/otlp-exporter-base"); const zlib_1 = require("zlib"); const core_1 = require("@opentelemetry/core"); const aws_authenticator_1 = require("./aws-authenticator"); /** * Base class for AWS OTLP exporters */ class OTLPAwsBaseExporter extends otlp_exporter_base_1.OTLPExporterBase { constructor(endpoint, service, parentExporter, parentSerializer, compression) { super(parentExporter['_delegate']); this.compression = compression; this.endpoint = endpoint; this.authenticator = new aws_authenticator_1.AwsAuthenticator(this.endpoint, service); this.parentExporter = parentExporter; this.parentSerializer = parentSerializer; // To prevent performance degradation from serializing and compressing data twice, we handle serialization and compression // locally in this exporter and pass the pre-processed data to the upstream export. // This is used in order to prevent serializing and compressing the data again when calling parentExporter.export(). // To see why this works: // https://github.com/open-telemetry/opentelemetry-js/blob/ec17ce48d0e5a99a122da5add612a20e2dd84ed5/experimental/packages/otlp-exporter-base/src/otlp-export-delegate.ts#L69 this.serializer = new PassthroughSerializer(this.parentSerializer.deserializeResponse); this.parentExporter['_delegate']._serializer = this.serializer; } /** * Overrides the upstream implementation of export. * All behaviors are the same except if the endpoint is an AWS OTLP endpoint, we will sign the request with SigV4 * in headers before sending it to the endpoint. * @param items - Array of signal data to export * @param resultCallback - Callback function to handle export result */ async export(items, resultCallback) { var _a, _b, _c; // In OTel 2.x, headers() is an async function that returns a Promise const headersGetter = (_c = (_b = (_a = this.parentExporter['_delegate']._transport) === null || _a === void 0 ? void 0 : _a._transport) === null || _b === void 0 ? void 0 : _b._parameters) === null || _c === void 0 ? void 0 : _c.headers; if (!headersGetter) { resultCallback({ code: core_1.ExportResultCode.FAILED, error: new Error(`Request headers are unset - unable to export to ${this.endpoint}`), }); return; } const headers = await headersGetter(); if (!headers) { resultCallback({ code: core_1.ExportResultCode.FAILED, error: new Error(`Headers returned undefined - unable to export to ${this.endpoint}`), }); return; } let serializedData = this.parentSerializer.serializeRequest(items); if (!serializedData) { resultCallback({ code: core_1.ExportResultCode.FAILED, error: new Error('Nothing to send'), }); return; } delete headers['Content-Encoding']; const shouldCompress = this.compression && this.compression !== otlp_exporter_base_1.CompressionAlgorithm.NONE; if (shouldCompress) { try { serializedData = (0, zlib_1.gzipSync)(serializedData); headers['Content-Encoding'] = 'gzip'; } catch (exception) { resultCallback({ code: core_1.ExportResultCode.FAILED, error: new Error(`Failed to compress: ${exception}`), }); return; } } this.serializer.setSerializedData(serializedData); const signedHeaders = await this.authenticator.authenticate(headers, serializedData); if (!signedHeaders) { resultCallback({ code: core_1.ExportResultCode.FAILED, error: new Error('Sigv4 Signing Failed. Not exporting'), }); return; } // OTel 2.x expects an async headers function this.parentExporter['_delegate']._transport._transport._parameters.headers = async () => signedHeaders; this.parentExporter.export(items, resultCallback); } shutdown() { return this.parentExporter.shutdown(); } forceFlush() { return this.parentExporter.forceFlush(); } } exports.OTLPAwsBaseExporter = OTLPAwsBaseExporter; /** * A serializer that bypasses request serialization by returning pre-serialized data. * @template Response The type of the deserialized response */ class PassthroughSerializer { /** * Creates a new PassthroughSerializer instance. * @param deserializer Function to deserialize response data */ constructor(deserializer) { this.serializedData = new Uint8Array(); this.deserializer = deserializer; } /** * Sets the pre-serialized data to be returned when serializeRequest is called. * @param data The serialized data to use */ setSerializedData(data) { this.serializedData = data; } /** * Returns the pre-serialized data, ignoring the request parameter. * @param request Ignored parameter. * @returns The pre-serialized data */ serializeRequest(request) { return this.serializedData; } /** * Deserializes response data using the provided deserializer function. * @param data The response data to deserialize * @returns The deserialized response */ deserializeResponse(data) { return this.deserializer(data); } } //# sourceMappingURL=otlp-aws-base-exporter.js.map