pragma-log-manager-aws-lambda 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.es.md ADDED
@@ -0,0 +1,82 @@
1
+ # Log Builder For AWS Lambda JS with OpenTelemetry And Winston
2
+
3
+ ## Descripción
4
+ Una implementación de OpenTelemetry (OTEL) para Winston que proporciona trazabilidad para funciones AWS Lambda en Node.js.
5
+
6
+ ## Instalación
7
+
8
+ ```bash
9
+ npm i pragma-log-manager-aws-lambda
10
+ ```
11
+
12
+ ## Requisitos
13
+ Este paquete tiene las siguientes dependencias:
14
+ - @opentelemetry/api: ^1.9.0
15
+ - @opentelemetry/auto-instrumentations-node: ^0.52.0
16
+ - @opentelemetry/exporter-trace-otlp-http: ^0.52.0
17
+ - @opentelemetry/instrumentation-aws-lambda: ^0.52.0
18
+ - @opentelemetry/resources: ^1.19.0
19
+ - @opentelemetry/sdk-node: ^0.52.1
20
+ - @opentelemetry/semantic-conventions: ^1.19.0
21
+ - winston: ^3.17.0
22
+
23
+ ## Uso
24
+
25
+ ### Configuración básica
26
+
27
+ ```javascript
28
+ import { logger, wrapLambdaHandler } from 'winston-otel-pragma-logs';
29
+
30
+ // Función Lambda original
31
+ const myHandler = async (event, context) => {
32
+ // Registrar un mensaje con información de trazabilidad
33
+ logger.info('Procesando evento', { action: { eventData: event } });
34
+
35
+ // Tu lógica de negocio aquí
36
+ const result = await procesarDatos(event);
37
+
38
+ logger.info('Procesamiento completado', { action: { resultado: result } });
39
+ return result;
40
+ };
41
+
42
+ // Exportar el handler envuelto con trazabilidad
43
+ export const handler = wrapLambdaHandler(myHandler);
44
+ ```
45
+
46
+ ### Configuración de variables de entorno
47
+
48
+ El paquete utiliza las siguientes variables de entorno:
49
+
50
+ - `OTEL_EXPORTER_OTLP_ENDPOINT`: URL del endpoint para exportar trazas OTLP (por ejemplo, "https://api.honeycomb.io/v1/traces")
51
+ - `OTEL_SERVICE_NAME`: Nombre del servicio para identificar tu aplicación en las trazas (por defecto: "default-lambda")
52
+
53
+ ## Formato de logs
54
+
55
+ Los logs generados incluyen automáticamente información de trazabilidad en formato JSON:
56
+
57
+ ```json
58
+ {
59
+ "timestamp": "2023-06-15T12:34:56.789Z",
60
+ "tracing": {
61
+ "traceId": "abcdef1234567890abcdef1234567890",
62
+ "spanId": "abcdef1234567890"
63
+ },
64
+ "level": "info",
65
+ "message": "Mensaje de log",
66
+ "data": {
67
+ "clave": "valor",
68
+ "otrosDatos": 123
69
+ }
70
+ }
71
+ ```
72
+
73
+ ## Características
74
+
75
+ - Integración automática de Winston con OpenTelemetry
76
+ - Wrapper para funciones Lambda que crea spans automáticamente
77
+ - Correlación automática entre logs y trazas
78
+ - Instrumentación automática para AWS Lambda y otras bibliotecas de Node.js
79
+ - Exportación de trazas a cualquier backend compatible con OTLP
80
+
81
+ ## Licencia
82
+ Desarrollado por [juan.ojeda@pragma.com.co](mailto:juan.ojeda@pragma.com.co)
package/README.md ADDED
@@ -0,0 +1,85 @@
1
+ # winston-otel-pragma-logs
2
+
3
+ ## Description
4
+ An OpenTelemetry (OTEL) implementation for Winston that provides tracing for AWS Lambda functions in Node.js.
5
+
6
+ ## Installation
7
+
8
+ ```bash
9
+ npm i pragma-log-manager-aws-lambda
10
+ ```
11
+
12
+ ## Requirements
13
+ This package has the following peer dependencies:
14
+ - @opentelemetry/api: ^1.9.0
15
+ - @opentelemetry/auto-instrumentations-node: ^0.52.0
16
+ - @opentelemetry/exporter-trace-otlp-http: ^0.52.0
17
+ - @opentelemetry/instrumentation-aws-lambda: ^0.52.0
18
+ - @opentelemetry/resources: ^1.19.0
19
+ - @opentelemetry/sdk-node: ^0.52.1
20
+ - @opentelemetry/semantic-conventions: ^1.19.0
21
+ - winston: ^3.17.0
22
+
23
+ ## Usage
24
+
25
+ ### Basic Configuration
26
+
27
+ ```javascript
28
+ import { logger, wrapLambdaHandler } from 'winston-otel-pragma-logs';
29
+
30
+ // Original Lambda function
31
+ const myHandler = async (event, context) => {
32
+ // Log a message with tracing information
33
+ logger.info('Processing event', { action: { eventData: event } });
34
+
35
+ // Your business logic here
36
+ const result = await processData(event);
37
+
38
+ logger.info('Processing completed', { action: { result: result } });
39
+ return result;
40
+ };
41
+
42
+ // Export the wrapped handler with tracing
43
+ export const handler = wrapLambdaHandler(myHandler);
44
+ ```
45
+
46
+ ### Environment Variables Configuration
47
+
48
+ The package uses the following environment variables:
49
+
50
+ - `OTEL_EXPORTER_OTLP_ENDPOINT`: URL of the endpoint to export OTLP traces (e.g., "https://api.honeycomb.io/v1/traces")
51
+ - `OTEL_SERVICE_NAME`: Service name to identify your application in traces (default: "default-lambda")
52
+
53
+ ## Log Format
54
+
55
+ The generated logs automatically include tracing information in JSON format:
56
+
57
+ ```json
58
+ {
59
+ "timestamp": "2023-06-15T12:34:56.789Z",
60
+ "tracing": {
61
+ "traceId": "abcdef1234567890abcdef1234567890",
62
+ "spanId": "abcdef1234567890"
63
+ },
64
+ "level": "info",
65
+ "message": "Log message",
66
+ "data": {
67
+ "key": "value",
68
+ "otherData": 123
69
+ }
70
+ }
71
+ ```
72
+
73
+ ## Features
74
+
75
+ - Automatic integration of Winston with OpenTelemetry
76
+ - Wrapper for Lambda functions that automatically creates spans
77
+ - Automatic correlation between logs and traces
78
+ - Automatic instrumentation for AWS Lambda and other Node.js libraries
79
+ - Export traces to any OTLP-compatible backend
80
+
81
+ ## Spanish Documentation
82
+ For Spanish documentation, please see [README.es.md](README.es.md).
83
+
84
+ ## License
85
+ Developed by [juan.ojeda@pragma.com.co](mailto:juan.ojeda@pragma.com.co)
@@ -0,0 +1,2 @@
1
+ export * from './logger';
2
+ export * from './wrapper';
@@ -0,0 +1,18 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ __exportStar(require("./logger"), exports);
18
+ __exportStar(require("./wrapper"), exports);
@@ -0,0 +1,3 @@
1
+ import * as winston from "winston";
2
+ import './tracing';
3
+ export declare const logger: winston.Logger;
@@ -0,0 +1,67 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.logger = void 0;
37
+ const winston = __importStar(require("winston"));
38
+ const moment = __importStar(require("moment-timezone"));
39
+ require("./tracing");
40
+ const tracing_1 = require("./tracing");
41
+ exports.logger = winston.createLogger({
42
+ level: 'info',
43
+ format: winston.format.combine(winston.format.timestamp({
44
+ format: () => moment.tz('America/Bogota').format('YYYY-MM-DDTHH:mm:ss.SSS')
45
+ }), winston.format.printf(({ level, message, timestamp, ...obj }) => {
46
+ const { traceId, spanId } = (0, tracing_1.getCurrentTrace)();
47
+ const payload = obj.action;
48
+ const error = obj.error;
49
+ const transactionId = obj.transactionId;
50
+ const log = {
51
+ timestamp,
52
+ severity: level,
53
+ transactionId: transactionId ?? 'Id Not Available',
54
+ message,
55
+ appName: process.env.OTEL_SERVICE_NAME,
56
+ appNamespace: process.env.OTEL_SERVICE_NAMESPACE ?? 'namespaceTest',
57
+ tracing: {
58
+ traceId,
59
+ spanId
60
+ },
61
+ action: payload,
62
+ error: error
63
+ };
64
+ return JSON.stringify(log);
65
+ })),
66
+ transports: [new winston.transports.Console()],
67
+ });
@@ -0,0 +1,5 @@
1
+ export declare const tracer: import("@opentelemetry/api").Tracer;
2
+ export declare const getCurrentTrace: () => {
3
+ traceId: string;
4
+ spanId: string;
5
+ };
@@ -0,0 +1,51 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getCurrentTrace = exports.tracer = void 0;
4
+ const sdk_node_1 = require("@opentelemetry/sdk-node");
5
+ const resources_1 = require("@opentelemetry/resources");
6
+ const semantic_conventions_1 = require("@opentelemetry/semantic-conventions");
7
+ const exporter_trace_otlp_http_1 = require("@opentelemetry/exporter-trace-otlp-http");
8
+ const instrumentation_aws_lambda_1 = require("@opentelemetry/instrumentation-aws-lambda");
9
+ const api_1 = require("@opentelemetry/api");
10
+ let sdk = null;
11
+ const initializeSDK = () => {
12
+ if (sdk)
13
+ return sdk;
14
+ const traceExporter = process.env.OTEL_EXPORTER_OTLP_ENDPOINT
15
+ ? new exporter_trace_otlp_http_1.OTLPTraceExporter({ url: process.env.OTEL_EXPORTER_OTLP_ENDPOINT })
16
+ : undefined;
17
+ sdk = new sdk_node_1.NodeSDK({
18
+ resource: new resources_1.Resource({
19
+ [semantic_conventions_1.ATTR_SERVICE_NAME]: process.env.OTEL_SERVICE_NAME || 'default-lambda',
20
+ }),
21
+ instrumentations: [
22
+ new instrumentation_aws_lambda_1.AwsLambdaInstrumentation()
23
+ ],
24
+ traceExporter: traceExporter
25
+ });
26
+ sdk.start();
27
+ return sdk;
28
+ };
29
+ // Initialize SDK
30
+ initializeSDK();
31
+ exports.tracer = api_1.trace.getTracer('default-tracer');
32
+ const getCurrentTrace = () => {
33
+ const activeSpan = api_1.trace.getActiveSpan();
34
+ if (!activeSpan) {
35
+ return {
36
+ traceId: 'no-trace-id',
37
+ spanId: 'no-span-id'
38
+ };
39
+ }
40
+ const spanContext = activeSpan.spanContext();
41
+ return {
42
+ traceId: spanContext.traceId,
43
+ spanId: spanContext.spanId
44
+ };
45
+ };
46
+ exports.getCurrentTrace = getCurrentTrace;
47
+ process.on('SIGTERM', () => {
48
+ if (sdk) {
49
+ sdk.shutdown().then();
50
+ }
51
+ });
@@ -0,0 +1,2 @@
1
+ import { Context } from 'aws-lambda';
2
+ export declare const wrapLambdaHandler: (handlerFunction: Function) => (event: any, context: Context) => Promise<any>;
@@ -0,0 +1,21 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.wrapLambdaHandler = void 0;
4
+ const tracing_1 = require("./tracing");
5
+ const wrapLambdaHandler = (handlerFunction) => {
6
+ return async (event, context) => {
7
+ return tracing_1.tracer.startActiveSpan('lambda-execution', async (span) => {
8
+ try {
9
+ const result = await handlerFunction(event, context);
10
+ span.end();
11
+ return result;
12
+ }
13
+ catch (error) {
14
+ span.recordException(error);
15
+ span.end();
16
+ throw error;
17
+ }
18
+ });
19
+ };
20
+ };
21
+ exports.wrapLambdaHandler = wrapLambdaHandler;
@@ -0,0 +1,2 @@
1
+ export * from './logger';
2
+ export * from './wrapper';
@@ -0,0 +1,2 @@
1
+ export * from './logger';
2
+ export * from './wrapper';
@@ -0,0 +1,3 @@
1
+ import * as winston from "winston";
2
+ import './tracing';
3
+ export declare const logger: winston.Logger;
@@ -0,0 +1,31 @@
1
+ import * as winston from "winston";
2
+ import * as moment from "moment-timezone";
3
+ import './tracing';
4
+ import { getCurrentTrace } from "./tracing";
5
+ export const logger = winston.createLogger({
6
+ level: 'info',
7
+ format: winston.format.combine(winston.format.timestamp({
8
+ format: () => moment.tz('America/Bogota').format('YYYY-MM-DDTHH:mm:ss.SSS')
9
+ }), winston.format.printf(({ level, message, timestamp, ...obj }) => {
10
+ const { traceId, spanId } = getCurrentTrace();
11
+ const payload = obj.action;
12
+ const error = obj.error;
13
+ const transactionId = obj.transactionId;
14
+ const log = {
15
+ timestamp,
16
+ severity: level,
17
+ transactionId: transactionId ?? 'Id Not Available',
18
+ message,
19
+ appName: process.env.OTEL_SERVICE_NAME,
20
+ appNamespace: process.env.OTEL_SERVICE_NAMESPACE ?? 'namespaceTest',
21
+ tracing: {
22
+ traceId,
23
+ spanId
24
+ },
25
+ action: payload,
26
+ error: error
27
+ };
28
+ return JSON.stringify(log);
29
+ })),
30
+ transports: [new winston.transports.Console()],
31
+ });
@@ -0,0 +1,5 @@
1
+ export declare const tracer: import("@opentelemetry/api").Tracer;
2
+ export declare const getCurrentTrace: () => {
3
+ traceId: string;
4
+ spanId: string;
5
+ };
@@ -0,0 +1,47 @@
1
+ import { NodeSDK } from '@opentelemetry/sdk-node';
2
+ import { Resource } from '@opentelemetry/resources';
3
+ import { ATTR_SERVICE_NAME } from '@opentelemetry/semantic-conventions';
4
+ import { OTLPTraceExporter } from '@opentelemetry/exporter-trace-otlp-http';
5
+ import { AwsLambdaInstrumentation } from '@opentelemetry/instrumentation-aws-lambda';
6
+ import { trace } from '@opentelemetry/api';
7
+ let sdk = null;
8
+ const initializeSDK = () => {
9
+ if (sdk)
10
+ return sdk;
11
+ const traceExporter = process.env.OTEL_EXPORTER_OTLP_ENDPOINT
12
+ ? new OTLPTraceExporter({ url: process.env.OTEL_EXPORTER_OTLP_ENDPOINT })
13
+ : undefined;
14
+ sdk = new NodeSDK({
15
+ resource: new Resource({
16
+ [ATTR_SERVICE_NAME]: process.env.OTEL_SERVICE_NAME || 'default-lambda',
17
+ }),
18
+ instrumentations: [
19
+ new AwsLambdaInstrumentation()
20
+ ],
21
+ traceExporter: traceExporter
22
+ });
23
+ sdk.start();
24
+ return sdk;
25
+ };
26
+ // Initialize SDK
27
+ initializeSDK();
28
+ export const tracer = trace.getTracer('default-tracer');
29
+ export const getCurrentTrace = () => {
30
+ const activeSpan = trace.getActiveSpan();
31
+ if (!activeSpan) {
32
+ return {
33
+ traceId: 'no-trace-id',
34
+ spanId: 'no-span-id'
35
+ };
36
+ }
37
+ const spanContext = activeSpan.spanContext();
38
+ return {
39
+ traceId: spanContext.traceId,
40
+ spanId: spanContext.spanId
41
+ };
42
+ };
43
+ process.on('SIGTERM', () => {
44
+ if (sdk) {
45
+ sdk.shutdown().then();
46
+ }
47
+ });
@@ -0,0 +1,2 @@
1
+ import { Context } from 'aws-lambda';
2
+ export declare const wrapLambdaHandler: (handlerFunction: Function) => (event: any, context: Context) => Promise<any>;
@@ -0,0 +1,17 @@
1
+ import { tracer } from './tracing';
2
+ export const wrapLambdaHandler = (handlerFunction) => {
3
+ return async (event, context) => {
4
+ return tracer.startActiveSpan('lambda-execution', async (span) => {
5
+ try {
6
+ const result = await handlerFunction(event, context);
7
+ span.end();
8
+ return result;
9
+ }
10
+ catch (error) {
11
+ span.recordException(error);
12
+ span.end();
13
+ throw error;
14
+ }
15
+ });
16
+ };
17
+ };
@@ -0,0 +1,2 @@
1
+ export * from './logger';
2
+ export * from './wrapper';
@@ -0,0 +1,3 @@
1
+ import * as winston from "winston";
2
+ import './tracing';
3
+ export declare const logger: winston.Logger;
@@ -0,0 +1,5 @@
1
+ export declare const tracer: import("@opentelemetry/api").Tracer;
2
+ export declare const getCurrentTrace: () => {
3
+ traceId: string;
4
+ spanId: string;
5
+ };
@@ -0,0 +1,2 @@
1
+ import { Context } from 'aws-lambda';
2
+ export declare const wrapLambdaHandler: (handlerFunction: Function) => (event: any, context: Context) => Promise<any>;
package/package.json ADDED
@@ -0,0 +1,46 @@
1
+ {
2
+ "name": "pragma-log-manager-aws-lambda",
3
+ "version": "1.0.0",
4
+ "type": "commonjs",
5
+ "description": "OTEL - Winston implementation tracing for aws node lambdas in js",
6
+ "author": "juan.ojeda@pragma.com.co",
7
+ "exports": {
8
+ ".": {
9
+ "import": "./dist/esm/index.js",
10
+ "require": "./dist/cjs/index.js"
11
+ }
12
+ },
13
+ "main": "./dist/cjs/index.js",
14
+ "module": "./dist/esm/index.js",
15
+ "files": [
16
+ "dist"
17
+ ],
18
+ "scripts": {
19
+ "build": "npm run build:cjs && npm run build:esm && npm run build:types",
20
+ "build:cjs": "tsc --project tsconfig.cjs.json",
21
+ "build:esm": "tsc --project tsconfig.esm.json",
22
+ "build:types": "tsc --project tsconfig.types.json"
23
+ },
24
+ "peerDependencies": {
25
+ "@opentelemetry/api": "^1.9.0",
26
+ "@opentelemetry/auto-instrumentations-node": "^0.52.0",
27
+ "@opentelemetry/exporter-trace-otlp-http": "^0.52.0",
28
+ "@opentelemetry/instrumentation-aws-lambda": "^0.52.0",
29
+ "@opentelemetry/resources": "^1.19.0",
30
+ "@opentelemetry/sdk-node": "^0.52.1",
31
+ "@opentelemetry/semantic-conventions": "^1.19.0",
32
+ "winston": "^3.17.0"
33
+ },
34
+ "devDependencies": {
35
+ "typescript": "^5.4.0"
36
+ },
37
+ "dependencies": {
38
+ "moment-timezone": "^0.6.0"
39
+ },
40
+ "overrides": {
41
+ "protobufjs": "^7.5.5"
42
+ },
43
+ "resolutions": {
44
+ "protobufjs": "^7.5.5"
45
+ }
46
+ }