autotel-aws 0.2.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/LICENSE +21 -0
- package/README.md +540 -0
- package/dist/attributes.cjs +49 -0
- package/dist/attributes.cjs.map +1 -0
- package/dist/attributes.d.cts +117 -0
- package/dist/attributes.d.ts +117 -0
- package/dist/attributes.js +4 -0
- package/dist/attributes.js.map +1 -0
- package/dist/chunk-35F3UBOO.cjs +48 -0
- package/dist/chunk-35F3UBOO.cjs.map +1 -0
- package/dist/chunk-4TGVGEUN.cjs +84 -0
- package/dist/chunk-4TGVGEUN.cjs.map +1 -0
- package/dist/chunk-CIGXV6HA.js +192 -0
- package/dist/chunk-CIGXV6HA.js.map +1 -0
- package/dist/chunk-D5INYMRP.cjs +350 -0
- package/dist/chunk-D5INYMRP.cjs.map +1 -0
- package/dist/chunk-DF5PT3JK.js +387 -0
- package/dist/chunk-DF5PT3JK.js.map +1 -0
- package/dist/chunk-DGUM43GV.js +10 -0
- package/dist/chunk-DGUM43GV.js.map +1 -0
- package/dist/chunk-DHHLKZHI.cjs +23 -0
- package/dist/chunk-DHHLKZHI.cjs.map +1 -0
- package/dist/chunk-FKZOELBT.js +78 -0
- package/dist/chunk-FKZOELBT.js.map +1 -0
- package/dist/chunk-HMTKKKKP.cjs +390 -0
- package/dist/chunk-HMTKKKKP.cjs.map +1 -0
- package/dist/chunk-I4CKQ4RD.js +153 -0
- package/dist/chunk-I4CKQ4RD.js.map +1 -0
- package/dist/chunk-JEQ2X3Z6.cjs +12 -0
- package/dist/chunk-JEQ2X3Z6.cjs.map +1 -0
- package/dist/chunk-JMSFE6FJ.js +24 -0
- package/dist/chunk-JMSFE6FJ.js.map +1 -0
- package/dist/chunk-KUIOI74B.cjs +394 -0
- package/dist/chunk-KUIOI74B.cjs.map +1 -0
- package/dist/chunk-NQ65Y5AI.cjs +195 -0
- package/dist/chunk-NQ65Y5AI.cjs.map +1 -0
- package/dist/chunk-OB4XTAVK.cjs +345 -0
- package/dist/chunk-OB4XTAVK.cjs.map +1 -0
- package/dist/chunk-OHFR7WX5.js +341 -0
- package/dist/chunk-OHFR7WX5.js.map +1 -0
- package/dist/chunk-PZGYL7XZ.js +40 -0
- package/dist/chunk-PZGYL7XZ.js.map +1 -0
- package/dist/chunk-Q3DMMQ7K.cjs +164 -0
- package/dist/chunk-Q3DMMQ7K.cjs.map +1 -0
- package/dist/chunk-UZEJV2YD.cjs +139 -0
- package/dist/chunk-UZEJV2YD.cjs.map +1 -0
- package/dist/chunk-V4IQWFYN.js +341 -0
- package/dist/chunk-V4IQWFYN.js.map +1 -0
- package/dist/chunk-VZHQH75L.cjs +26 -0
- package/dist/chunk-VZHQH75L.cjs.map +1 -0
- package/dist/chunk-X6BY6PCK.js +386 -0
- package/dist/chunk-X6BY6PCK.js.map +1 -0
- package/dist/chunk-YG56NRIO.js +131 -0
- package/dist/chunk-YG56NRIO.js.map +1 -0
- package/dist/chunk-ZPDRKCAR.js +21 -0
- package/dist/chunk-ZPDRKCAR.js.map +1 -0
- package/dist/config-C7zV8Zm6.d.cts +125 -0
- package/dist/config-DxjTT8jd.d.ts +125 -0
- package/dist/dynamodb.cjs +14 -0
- package/dist/dynamodb.cjs.map +1 -0
- package/dist/dynamodb.d.cts +93 -0
- package/dist/dynamodb.d.ts +93 -0
- package/dist/dynamodb.js +5 -0
- package/dist/dynamodb.js.map +1 -0
- package/dist/eventbridge.cjs +279 -0
- package/dist/eventbridge.cjs.map +1 -0
- package/dist/eventbridge.d.cts +360 -0
- package/dist/eventbridge.d.ts +360 -0
- package/dist/eventbridge.js +273 -0
- package/dist/eventbridge.js.map +1 -0
- package/dist/index.cjs +251 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +126 -0
- package/dist/index.d.ts +126 -0
- package/dist/index.js +48 -0
- package/dist/index.js.map +1 -0
- package/dist/kinesis.cjs +23 -0
- package/dist/kinesis.cjs.map +1 -0
- package/dist/kinesis.d.cts +360 -0
- package/dist/kinesis.d.ts +360 -0
- package/dist/kinesis.js +6 -0
- package/dist/kinesis.js.map +1 -0
- package/dist/lambda-auto.cjs +19 -0
- package/dist/lambda-auto.cjs.map +1 -0
- package/dist/lambda-auto.d.cts +2 -0
- package/dist/lambda-auto.d.ts +2 -0
- package/dist/lambda-auto.js +17 -0
- package/dist/lambda-auto.js.map +1 -0
- package/dist/lambda.cjs +42 -0
- package/dist/lambda.cjs.map +1 -0
- package/dist/lambda.d.cts +231 -0
- package/dist/lambda.d.ts +231 -0
- package/dist/lambda.js +5 -0
- package/dist/lambda.js.map +1 -0
- package/dist/s3.cjs +14 -0
- package/dist/s3.cjs.map +1 -0
- package/dist/s3.d.cts +77 -0
- package/dist/s3.d.ts +77 -0
- package/dist/s3.js +5 -0
- package/dist/s3.js.map +1 -0
- package/dist/sdk.cjs +31 -0
- package/dist/sdk.cjs.map +1 -0
- package/dist/sdk.d.cts +155 -0
- package/dist/sdk.d.ts +155 -0
- package/dist/sdk.js +6 -0
- package/dist/sdk.js.map +1 -0
- package/dist/sns.cjs +19 -0
- package/dist/sns.cjs.map +1 -0
- package/dist/sns.d.cts +256 -0
- package/dist/sns.d.ts +256 -0
- package/dist/sns.js +6 -0
- package/dist/sns.js.map +1 -0
- package/dist/sqs.cjs +23 -0
- package/dist/sqs.cjs.map +1 -0
- package/dist/sqs.d.cts +384 -0
- package/dist/sqs.d.ts +384 -0
- package/dist/sqs.js +6 -0
- package/dist/sqs.js.map +1 -0
- package/dist/step-functions.cjs +35 -0
- package/dist/step-functions.cjs.map +1 -0
- package/dist/step-functions.d.cts +423 -0
- package/dist/step-functions.d.ts +423 -0
- package/dist/step-functions.js +6 -0
- package/dist/step-functions.js.map +1 -0
- package/dist/testing.cjs +61 -0
- package/dist/testing.cjs.map +1 -0
- package/dist/testing.d.cts +39 -0
- package/dist/testing.d.ts +39 -0
- package/dist/testing.js +58 -0
- package/dist/testing.js.map +1 -0
- package/dist/types-3_ak5jhy.d.cts +76 -0
- package/dist/types-3_ak5jhy.d.ts +76 -0
- package/dist/types-UiBv_I_M.d.ts +16 -0
- package/dist/types-kTFVdSqO.d.cts +16 -0
- package/dist/xray.cjs +26 -0
- package/dist/xray.cjs.map +1 -0
- package/dist/xray.d.cts +23 -0
- package/dist/xray.d.ts +23 -0
- package/dist/xray.js +5 -0
- package/dist/xray.js.map +1 -0
- package/package.json +184 -0
|
@@ -0,0 +1,386 @@
|
|
|
1
|
+
import { wrapSDKClient } from './chunk-YG56NRIO.js';
|
|
2
|
+
import { buildKinesisAttributes } from './chunk-I4CKQ4RD.js';
|
|
3
|
+
import { trace } from 'autotel';
|
|
4
|
+
import { propagation, context, SpanStatusCode } from '@opentelemetry/api';
|
|
5
|
+
|
|
6
|
+
function traceKinesis(config) {
|
|
7
|
+
return function wrapper(fn) {
|
|
8
|
+
return trace(
|
|
9
|
+
`kinesis.${config.operation}`,
|
|
10
|
+
(ctx) => async (...args) => {
|
|
11
|
+
ctx.setAttributes(
|
|
12
|
+
buildKinesisAttributes({
|
|
13
|
+
streamName: config.streamName,
|
|
14
|
+
shardId: config.shardId,
|
|
15
|
+
operation: config.operation
|
|
16
|
+
})
|
|
17
|
+
);
|
|
18
|
+
const handler = fn(ctx);
|
|
19
|
+
return handler(...args);
|
|
20
|
+
}
|
|
21
|
+
);
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
var KinesisProducer = class {
|
|
25
|
+
client;
|
|
26
|
+
config;
|
|
27
|
+
constructor(client, config) {
|
|
28
|
+
this.client = wrapSDKClient(client, config.service);
|
|
29
|
+
this.config = {
|
|
30
|
+
injectTraceContext: true,
|
|
31
|
+
...config
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Inject trace context into record data
|
|
36
|
+
*/
|
|
37
|
+
injectContext(data) {
|
|
38
|
+
let payload;
|
|
39
|
+
if (typeof data === "string") {
|
|
40
|
+
try {
|
|
41
|
+
payload = JSON.parse(data);
|
|
42
|
+
} catch {
|
|
43
|
+
payload = { _data: data };
|
|
44
|
+
}
|
|
45
|
+
} else {
|
|
46
|
+
payload = data;
|
|
47
|
+
}
|
|
48
|
+
if (this.config.injectTraceContext) {
|
|
49
|
+
const carrier = {};
|
|
50
|
+
propagation.inject(context.active(), carrier);
|
|
51
|
+
if (carrier.traceparent) {
|
|
52
|
+
payload = {
|
|
53
|
+
...payload,
|
|
54
|
+
_traceContext: {
|
|
55
|
+
traceparent: carrier.traceparent,
|
|
56
|
+
tracestate: carrier.tracestate,
|
|
57
|
+
baggage: carrier.baggage
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
return Buffer.from(JSON.stringify(payload));
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Put a single record to the stream
|
|
66
|
+
*
|
|
67
|
+
* @param record - Record to put
|
|
68
|
+
* @returns Promise with shard ID and sequence number
|
|
69
|
+
*/
|
|
70
|
+
async putRecord(record) {
|
|
71
|
+
return trace(`kinesis.put`, async (ctx) => {
|
|
72
|
+
ctx.setAttributes(
|
|
73
|
+
buildKinesisAttributes({
|
|
74
|
+
streamName: this.config.streamName,
|
|
75
|
+
operation: "put"
|
|
76
|
+
})
|
|
77
|
+
);
|
|
78
|
+
const input = {
|
|
79
|
+
StreamName: this.config.streamName,
|
|
80
|
+
Data: this.injectContext(record.data),
|
|
81
|
+
PartitionKey: record.partitionKey,
|
|
82
|
+
...record.explicitHashKey && { ExplicitHashKey: record.explicitHashKey },
|
|
83
|
+
...record.sequenceNumberForOrdering && {
|
|
84
|
+
SequenceNumberForOrdering: record.sequenceNumberForOrdering
|
|
85
|
+
}
|
|
86
|
+
};
|
|
87
|
+
try {
|
|
88
|
+
const { PutRecordCommand } = await import('@aws-sdk/client-kinesis');
|
|
89
|
+
const result = await this.client.send(new PutRecordCommand(input));
|
|
90
|
+
if (result.ShardId) {
|
|
91
|
+
ctx.setAttribute("aws.kinesis.shard_id", result.ShardId);
|
|
92
|
+
}
|
|
93
|
+
if (result.SequenceNumber) {
|
|
94
|
+
ctx.setAttribute("aws.kinesis.sequence_number", result.SequenceNumber);
|
|
95
|
+
}
|
|
96
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
97
|
+
return {
|
|
98
|
+
shardId: result.ShardId,
|
|
99
|
+
sequenceNumber: result.SequenceNumber,
|
|
100
|
+
encryptionType: result.EncryptionType
|
|
101
|
+
};
|
|
102
|
+
} catch (error) {
|
|
103
|
+
ctx.setStatus({
|
|
104
|
+
code: SpanStatusCode.ERROR,
|
|
105
|
+
message: error instanceof Error ? error.message : "Put failed"
|
|
106
|
+
});
|
|
107
|
+
throw error;
|
|
108
|
+
}
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
/**
|
|
112
|
+
* Put multiple records in a batch
|
|
113
|
+
*
|
|
114
|
+
* @param records - Array of records to put (max 500)
|
|
115
|
+
* @returns Promise with successful and failed record results
|
|
116
|
+
*/
|
|
117
|
+
async putRecords(records) {
|
|
118
|
+
return trace(`kinesis.putBatch`, async (ctx) => {
|
|
119
|
+
ctx.setAttributes(
|
|
120
|
+
buildKinesisAttributes({
|
|
121
|
+
streamName: this.config.streamName,
|
|
122
|
+
operation: "put"
|
|
123
|
+
})
|
|
124
|
+
);
|
|
125
|
+
ctx.setAttribute("messaging.batch.message_count", records.length);
|
|
126
|
+
const entries = records.map((record) => ({
|
|
127
|
+
Data: this.injectContext(record.data),
|
|
128
|
+
PartitionKey: record.partitionKey,
|
|
129
|
+
...record.explicitHashKey && { ExplicitHashKey: record.explicitHashKey }
|
|
130
|
+
}));
|
|
131
|
+
try {
|
|
132
|
+
const { PutRecordsCommand } = await import('@aws-sdk/client-kinesis');
|
|
133
|
+
const result = await this.client.send(
|
|
134
|
+
new PutRecordsCommand({
|
|
135
|
+
StreamName: this.config.streamName,
|
|
136
|
+
Records: entries
|
|
137
|
+
})
|
|
138
|
+
);
|
|
139
|
+
const successful = [];
|
|
140
|
+
const failed = [];
|
|
141
|
+
if (result.Records) {
|
|
142
|
+
for (const r of result.Records) {
|
|
143
|
+
const record = r;
|
|
144
|
+
if (record.ErrorCode) {
|
|
145
|
+
failed.push({ errorCode: record.ErrorCode, errorMessage: record.ErrorMessage });
|
|
146
|
+
} else {
|
|
147
|
+
successful.push({ shardId: record.ShardId, sequenceNumber: record.SequenceNumber });
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
ctx.setAttribute("messaging.kinesis.successful_count", successful.length);
|
|
152
|
+
ctx.setAttribute("messaging.kinesis.failed_count", result.FailedRecordCount || 0);
|
|
153
|
+
if (result.FailedRecordCount && result.FailedRecordCount > 0) {
|
|
154
|
+
ctx.setStatus({
|
|
155
|
+
code: SpanStatusCode.ERROR,
|
|
156
|
+
message: `${result.FailedRecordCount} records failed`
|
|
157
|
+
});
|
|
158
|
+
} else {
|
|
159
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
160
|
+
}
|
|
161
|
+
return {
|
|
162
|
+
successful,
|
|
163
|
+
failed,
|
|
164
|
+
failedRecordCount: result.FailedRecordCount || 0
|
|
165
|
+
};
|
|
166
|
+
} catch (error) {
|
|
167
|
+
ctx.setStatus({
|
|
168
|
+
code: SpanStatusCode.ERROR,
|
|
169
|
+
message: error instanceof Error ? error.message : "Batch put failed"
|
|
170
|
+
});
|
|
171
|
+
throw error;
|
|
172
|
+
}
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
};
|
|
176
|
+
var KinesisConsumer = class {
|
|
177
|
+
client;
|
|
178
|
+
config;
|
|
179
|
+
constructor(client, config) {
|
|
180
|
+
this.client = wrapSDKClient(client, config.service);
|
|
181
|
+
this.config = {
|
|
182
|
+
extractTraceContext: true,
|
|
183
|
+
...config
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
/**
|
|
187
|
+
* Extract trace context from record data
|
|
188
|
+
*/
|
|
189
|
+
extractContext(data) {
|
|
190
|
+
if (!this.config.extractTraceContext || !data?._traceContext) {
|
|
191
|
+
return void 0;
|
|
192
|
+
}
|
|
193
|
+
const tc = data._traceContext;
|
|
194
|
+
const carrier = {};
|
|
195
|
+
if (tc.traceparent) carrier.traceparent = tc.traceparent;
|
|
196
|
+
if (tc.tracestate) carrier.tracestate = tc.tracestate;
|
|
197
|
+
if (tc.baggage) carrier.baggage = tc.baggage;
|
|
198
|
+
return Object.keys(carrier).length > 0 ? carrier : void 0;
|
|
199
|
+
}
|
|
200
|
+
/**
|
|
201
|
+
* Parse raw record data
|
|
202
|
+
*/
|
|
203
|
+
parseRecord(record) {
|
|
204
|
+
const rawData = record.Data ? Buffer.from(record.Data).toString("utf8") : "";
|
|
205
|
+
let data;
|
|
206
|
+
try {
|
|
207
|
+
data = JSON.parse(rawData);
|
|
208
|
+
} catch {
|
|
209
|
+
data = rawData;
|
|
210
|
+
}
|
|
211
|
+
return {
|
|
212
|
+
sequenceNumber: record.SequenceNumber || "",
|
|
213
|
+
approximateArrivalTimestamp: record.ApproximateArrivalTimestamp,
|
|
214
|
+
data,
|
|
215
|
+
rawData,
|
|
216
|
+
partitionKey: record.PartitionKey || "",
|
|
217
|
+
encryptionType: record.EncryptionType,
|
|
218
|
+
raw: record
|
|
219
|
+
};
|
|
220
|
+
}
|
|
221
|
+
/**
|
|
222
|
+
* Get a shard iterator
|
|
223
|
+
*
|
|
224
|
+
* @param shardId - Shard ID
|
|
225
|
+
* @param type - Iterator type
|
|
226
|
+
* @param startingSequenceNumber - Starting sequence number (for AT_SEQUENCE_NUMBER, AFTER_SEQUENCE_NUMBER)
|
|
227
|
+
* @param timestamp - Starting timestamp (for AT_TIMESTAMP)
|
|
228
|
+
* @returns Shard iterator string
|
|
229
|
+
*/
|
|
230
|
+
async getShardIterator(shardId, type, startingSequenceNumber, timestamp) {
|
|
231
|
+
return trace(`kinesis.getShardIterator`, async (ctx) => {
|
|
232
|
+
ctx.setAttributes(
|
|
233
|
+
buildKinesisAttributes({
|
|
234
|
+
streamName: this.config.streamName,
|
|
235
|
+
shardId,
|
|
236
|
+
operation: "get"
|
|
237
|
+
})
|
|
238
|
+
);
|
|
239
|
+
try {
|
|
240
|
+
const { GetShardIteratorCommand } = await import('@aws-sdk/client-kinesis');
|
|
241
|
+
const result = await this.client.send(
|
|
242
|
+
new GetShardIteratorCommand({
|
|
243
|
+
StreamName: this.config.streamName,
|
|
244
|
+
ShardId: shardId,
|
|
245
|
+
ShardIteratorType: type,
|
|
246
|
+
...startingSequenceNumber && { StartingSequenceNumber: startingSequenceNumber },
|
|
247
|
+
...timestamp && { Timestamp: timestamp }
|
|
248
|
+
})
|
|
249
|
+
);
|
|
250
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
251
|
+
return result.ShardIterator || "";
|
|
252
|
+
} catch (error) {
|
|
253
|
+
ctx.setStatus({
|
|
254
|
+
code: SpanStatusCode.ERROR,
|
|
255
|
+
message: error instanceof Error ? error.message : "GetShardIterator failed"
|
|
256
|
+
});
|
|
257
|
+
throw error;
|
|
258
|
+
}
|
|
259
|
+
});
|
|
260
|
+
}
|
|
261
|
+
/**
|
|
262
|
+
* Get records from a shard iterator
|
|
263
|
+
*
|
|
264
|
+
* @param shardIterator - Shard iterator
|
|
265
|
+
* @param limit - Maximum records to return (max 10000)
|
|
266
|
+
* @returns Records and next shard iterator
|
|
267
|
+
*/
|
|
268
|
+
async getRecords(shardIterator, limit) {
|
|
269
|
+
return trace(`kinesis.get`, async (ctx) => {
|
|
270
|
+
ctx.setAttributes(
|
|
271
|
+
buildKinesisAttributes({
|
|
272
|
+
streamName: this.config.streamName,
|
|
273
|
+
operation: "get"
|
|
274
|
+
})
|
|
275
|
+
);
|
|
276
|
+
try {
|
|
277
|
+
const { GetRecordsCommand } = await import('@aws-sdk/client-kinesis');
|
|
278
|
+
const result = await this.client.send(
|
|
279
|
+
new GetRecordsCommand({
|
|
280
|
+
ShardIterator: shardIterator,
|
|
281
|
+
...limit && { Limit: limit }
|
|
282
|
+
})
|
|
283
|
+
);
|
|
284
|
+
const records = (result.Records || []).map((r) => this.parseRecord(r));
|
|
285
|
+
ctx.setAttribute("messaging.batch.message_count", records.length);
|
|
286
|
+
if (result.MillisBehindLatest !== void 0) {
|
|
287
|
+
ctx.setAttribute("aws.kinesis.millis_behind_latest", result.MillisBehindLatest);
|
|
288
|
+
}
|
|
289
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
290
|
+
return {
|
|
291
|
+
records,
|
|
292
|
+
nextIterator: result.NextShardIterator,
|
|
293
|
+
millisBehindLatest: result.MillisBehindLatest
|
|
294
|
+
};
|
|
295
|
+
} catch (error) {
|
|
296
|
+
ctx.setStatus({
|
|
297
|
+
code: SpanStatusCode.ERROR,
|
|
298
|
+
message: error instanceof Error ? error.message : "GetRecords failed"
|
|
299
|
+
});
|
|
300
|
+
throw error;
|
|
301
|
+
}
|
|
302
|
+
});
|
|
303
|
+
}
|
|
304
|
+
/**
|
|
305
|
+
* Process records with automatic trace context extraction
|
|
306
|
+
*
|
|
307
|
+
* @param shardIterator - Shard iterator
|
|
308
|
+
* @param processor - Function to process each record
|
|
309
|
+
* @param limit - Maximum records to process
|
|
310
|
+
* @returns Next shard iterator and count of processed records
|
|
311
|
+
*/
|
|
312
|
+
async processRecords(shardIterator, processor, limit) {
|
|
313
|
+
const { records, nextIterator } = await this.getRecords(shardIterator, limit);
|
|
314
|
+
let processedCount = 0;
|
|
315
|
+
for (const record of records) {
|
|
316
|
+
const carrier = this.extractContext(record.data);
|
|
317
|
+
const processRecord = async () => {
|
|
318
|
+
return trace(`kinesis.process`, async (ctx) => {
|
|
319
|
+
ctx.setAttributes(
|
|
320
|
+
buildKinesisAttributes({
|
|
321
|
+
streamName: this.config.streamName,
|
|
322
|
+
operation: "get"
|
|
323
|
+
})
|
|
324
|
+
);
|
|
325
|
+
ctx.setAttribute("aws.kinesis.sequence_number", record.sequenceNumber);
|
|
326
|
+
ctx.setAttribute("aws.kinesis.partition_key", record.partitionKey);
|
|
327
|
+
try {
|
|
328
|
+
await processor(record, ctx);
|
|
329
|
+
processedCount++;
|
|
330
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
331
|
+
} catch (error) {
|
|
332
|
+
ctx.setStatus({
|
|
333
|
+
code: SpanStatusCode.ERROR,
|
|
334
|
+
message: error instanceof Error ? error.message : "Processing failed"
|
|
335
|
+
});
|
|
336
|
+
throw error;
|
|
337
|
+
}
|
|
338
|
+
});
|
|
339
|
+
};
|
|
340
|
+
if (carrier) {
|
|
341
|
+
const extractedContext = propagation.extract(context.active(), carrier);
|
|
342
|
+
await context.with(extractedContext, processRecord);
|
|
343
|
+
} else {
|
|
344
|
+
await processRecord();
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
return { nextIterator, processedCount };
|
|
348
|
+
}
|
|
349
|
+
/**
|
|
350
|
+
* List shards for the stream
|
|
351
|
+
*
|
|
352
|
+
* @returns Array of shard IDs
|
|
353
|
+
*/
|
|
354
|
+
async listShards() {
|
|
355
|
+
return trace(`kinesis.listShards`, async (ctx) => {
|
|
356
|
+
ctx.setAttributes(
|
|
357
|
+
buildKinesisAttributes({
|
|
358
|
+
streamName: this.config.streamName,
|
|
359
|
+
operation: "get"
|
|
360
|
+
})
|
|
361
|
+
);
|
|
362
|
+
try {
|
|
363
|
+
const { ListShardsCommand } = await import('@aws-sdk/client-kinesis');
|
|
364
|
+
const result = await this.client.send(
|
|
365
|
+
new ListShardsCommand({
|
|
366
|
+
StreamName: this.config.streamName
|
|
367
|
+
})
|
|
368
|
+
);
|
|
369
|
+
const shardIds = result.Shards?.map((s) => s.ShardId || "") || [];
|
|
370
|
+
ctx.setAttribute("aws.kinesis.shard_count", shardIds.length);
|
|
371
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
372
|
+
return shardIds;
|
|
373
|
+
} catch (error) {
|
|
374
|
+
ctx.setStatus({
|
|
375
|
+
code: SpanStatusCode.ERROR,
|
|
376
|
+
message: error instanceof Error ? error.message : "ListShards failed"
|
|
377
|
+
});
|
|
378
|
+
throw error;
|
|
379
|
+
}
|
|
380
|
+
});
|
|
381
|
+
}
|
|
382
|
+
};
|
|
383
|
+
|
|
384
|
+
export { KinesisConsumer, KinesisProducer, traceKinesis };
|
|
385
|
+
//# sourceMappingURL=chunk-X6BY6PCK.js.map
|
|
386
|
+
//# sourceMappingURL=chunk-X6BY6PCK.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/kinesis/index.ts"],"names":[],"mappings":"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","file":"chunk-X6BY6PCK.js","sourcesContent":["/**\n * Kinesis-specific instrumentation\n *\n * Provides semantic helpers for tracing Kinesis Data Streams operations with proper\n * OpenTelemetry messaging semantic conventions.\n *\n * @example Put record to stream\n * ```typescript\n * import { traceKinesis } from 'autotel-aws/kinesis';\n * import { KinesisClient, PutRecordCommand } from '@aws-sdk/client-kinesis';\n *\n * const kinesis = new KinesisClient({});\n *\n * export const putRecord = traceKinesis({\n * operation: 'put',\n * streamName: 'my-stream'\n * })(ctx => async (data: object, partitionKey: string) => {\n * const result = await kinesis.send(new PutRecordCommand({\n * StreamName: 'my-stream',\n * Data: Buffer.from(JSON.stringify(data)),\n * PartitionKey: partitionKey\n * }));\n *\n * ctx.setAttribute('aws.kinesis.shard_id', result.ShardId ?? '');\n * ctx.setAttribute('aws.kinesis.sequence_number', result.SequenceNumber ?? '');\n *\n * return result;\n * });\n *\n * // Usage: await putRecord({ event: 'click' }, 'user-123');\n * ```\n *\n * @example Get records from shard\n * ```typescript\n * export const getRecords = traceKinesis({\n * operation: 'get',\n * streamName: 'my-stream'\n * })(ctx => async (shardIterator: string, limit: number) => {\n * const result = await kinesis.send(new GetRecordsCommand({\n * ShardIterator: shardIterator,\n * Limit: limit\n * }));\n *\n * ctx.setAttribute('messaging.batch.message_count', result.Records?.length ?? 0);\n * return result;\n * });\n * ```\n */\n\nimport { trace, type TraceContext } from 'autotel';\nimport { context, propagation, SpanStatusCode } from '@opentelemetry/api';\nimport { buildKinesisAttributes } from '../attributes';\nimport { wrapSDKClient } from '../common/sdk-wrapper';\n\n/**\n * Kinesis operation configuration\n */\nexport interface TraceKinesisConfig {\n /**\n * Kinesis operation type\n * - 'put' - PutRecord, PutRecords\n * - 'get' - GetRecords, GetShardIterator\n */\n operation: 'put' | 'get';\n\n /**\n * Kinesis stream name\n * Sets `messaging.destination.name` attribute.\n */\n streamName: string;\n\n /**\n * Shard ID (if known at configuration time)\n * Sets `aws.kinesis.shard_id` attribute.\n */\n shardId?: string;\n}\n\n/**\n * Trace Kinesis operations with semantic attributes\n *\n * Creates a traced function that automatically sets Kinesis messaging semantic attributes\n * following OpenTelemetry conventions.\n *\n * @param config - Kinesis operation configuration\n * @returns A higher-order function that wraps your Kinesis operation with tracing\n *\n * @remarks\n * Semantic attributes set automatically:\n * - `messaging.system` - 'aws_kinesis'\n * - `messaging.destination.name` - Stream name\n * - `messaging.operation` - 'put' or 'get'\n * - `aws.kinesis.shard_id` - Shard ID (if provided)\n *\n * Additional attributes you should set in your handler:\n * - `aws.kinesis.sequence_number` - Record sequence number\n * - `messaging.batch.message_count` - Number of records in batch\n *\n * @see https://opentelemetry.io/docs/specs/semconv/messaging/aws-kinesis/\n */\nexport function traceKinesis(config: TraceKinesisConfig) {\n return function wrapper<TArgs extends unknown[], TReturn>(\n fn: (ctx: TraceContext) => (...args: TArgs) => Promise<TReturn>,\n ): (...args: TArgs) => Promise<TReturn> {\n // Use autotel's trace() which properly handles the factory pattern\n return trace(\n `kinesis.${config.operation}`,\n (ctx: TraceContext) =>\n async (...args: TArgs): Promise<TReturn> => {\n // Set Kinesis semantic attributes\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: config.streamName,\n shardId: config.shardId,\n operation: config.operation,\n }),\n );\n\n // Get the user's handler and execute with forwarded arguments\n const handler = fn(ctx);\n return handler(...args);\n },\n );\n };\n}\n\n// ============================================================================\n// Kinesis Producer - Puts records with automatic trace context injection\n// ============================================================================\n\n/**\n * Configuration for Kinesis Producer\n */\nexport interface KinesisProducerConfig {\n /**\n * Kinesis stream name or ARN\n */\n streamName: string;\n\n /**\n * Inject W3C Trace Context into record data\n * Enables distributed tracing across producer/consumer\n * @default true\n */\n injectTraceContext?: boolean;\n\n /**\n * Optional service name for tracing\n */\n service?: string;\n}\n\n/**\n * Record to put via Kinesis Producer\n */\nexport interface KinesisRecord {\n /**\n * Record data (will be serialized to JSON if object)\n */\n data: string | object;\n\n /**\n * Partition key for sharding\n */\n partitionKey: string;\n\n /**\n * Optional explicit hash key\n */\n explicitHashKey?: string;\n\n /**\n * Optional sequence number for ordering\n */\n sequenceNumberForOrdering?: string;\n}\n\n/**\n * Kinesis Producer with automatic trace context injection\n *\n * Wraps a Kinesis client to automatically:\n * - Create spans for put operations\n * - Inject W3C Trace Context into record data\n * - Set proper semantic attributes\n *\n * @example Basic usage\n * ```typescript\n * import { KinesisProducer } from 'autotel-aws/kinesis';\n * import { KinesisClient } from '@aws-sdk/client-kinesis';\n *\n * const kinesis = new KinesisClient({ region: 'us-east-1' });\n * const producer = new KinesisProducer(kinesis, {\n * streamName: 'my-stream'\n * });\n *\n * // Put with automatic trace context\n * const result = await producer.putRecord({\n * data: { event: 'click', userId: '123' },\n * partitionKey: 'user-123'\n * });\n * console.log('Sequence:', result.sequenceNumber);\n * ```\n *\n * @example Batch put\n * ```typescript\n * const results = await producer.putRecords([\n * { data: { event: 'click' }, partitionKey: 'user-1' },\n * { data: { event: 'view' }, partitionKey: 'user-2' },\n * { data: { event: 'scroll' }, partitionKey: 'user-3' }\n * ]);\n * console.log(`Put ${results.successful.length} records`);\n * ```\n */\nexport class KinesisProducer<\n \n TClient extends { send: (command: any) => Promise<any> } = any,\n> {\n private client: TClient;\n private config: Required<Pick<KinesisProducerConfig, 'streamName'>> & KinesisProducerConfig;\n\n constructor(client: TClient, config: KinesisProducerConfig) {\n this.client = wrapSDKClient(client as any, config.service) as TClient;\n this.config = {\n injectTraceContext: true,\n ...config,\n };\n }\n\n /**\n * Inject trace context into record data\n */\n private injectContext(data: string | object): Buffer {\n let payload: object;\n\n if (typeof data === 'string') {\n try {\n payload = JSON.parse(data);\n } catch {\n // If not valid JSON, wrap in object\n payload = { _data: data };\n }\n } else {\n payload = data;\n }\n\n if (this.config.injectTraceContext) {\n const carrier: Record<string, string> = {};\n propagation.inject(context.active(), carrier);\n\n if (carrier.traceparent) {\n payload = {\n ...payload,\n _traceContext: {\n traceparent: carrier.traceparent,\n tracestate: carrier.tracestate,\n baggage: carrier.baggage,\n },\n };\n }\n }\n\n return Buffer.from(JSON.stringify(payload));\n }\n\n /**\n * Put a single record to the stream\n *\n * @param record - Record to put\n * @returns Promise with shard ID and sequence number\n */\n async putRecord(record: KinesisRecord): Promise<{\n shardId?: string;\n sequenceNumber?: string;\n encryptionType?: string;\n }> {\n return trace(`kinesis.put`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n operation: 'put',\n }),\n );\n\n const input = {\n StreamName: this.config.streamName,\n Data: this.injectContext(record.data),\n PartitionKey: record.partitionKey,\n ...(record.explicitHashKey && { ExplicitHashKey: record.explicitHashKey }),\n ...(record.sequenceNumberForOrdering && {\n SequenceNumberForOrdering: record.sequenceNumberForOrdering,\n }),\n };\n\n try {\n const { PutRecordCommand } = await import('@aws-sdk/client-kinesis');\n const result = await this.client.send(new PutRecordCommand(input));\n\n if (result.ShardId) {\n ctx.setAttribute('aws.kinesis.shard_id', result.ShardId);\n }\n if (result.SequenceNumber) {\n ctx.setAttribute('aws.kinesis.sequence_number', result.SequenceNumber);\n }\n\n ctx.setStatus({ code: SpanStatusCode.OK });\n\n return {\n shardId: result.ShardId,\n sequenceNumber: result.SequenceNumber,\n encryptionType: result.EncryptionType,\n };\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'Put failed',\n });\n throw error;\n }\n });\n }\n\n /**\n * Put multiple records in a batch\n *\n * @param records - Array of records to put (max 500)\n * @returns Promise with successful and failed record results\n */\n async putRecords(records: KinesisRecord[]): Promise<{\n successful: Array<{ shardId?: string; sequenceNumber?: string }>;\n failed: Array<{ errorCode?: string; errorMessage?: string }>;\n failedRecordCount: number;\n }> {\n return trace(`kinesis.putBatch`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n operation: 'put',\n }),\n );\n ctx.setAttribute('messaging.batch.message_count', records.length);\n\n const entries = records.map((record) => ({\n Data: this.injectContext(record.data),\n PartitionKey: record.partitionKey,\n ...(record.explicitHashKey && { ExplicitHashKey: record.explicitHashKey }),\n }));\n\n try {\n const { PutRecordsCommand } = await import('@aws-sdk/client-kinesis');\n const result = await this.client.send(\n new PutRecordsCommand({\n StreamName: this.config.streamName,\n Records: entries,\n }),\n );\n\n const successful: Array<{ shardId?: string; sequenceNumber?: string }> = [];\n const failed: Array<{ errorCode?: string; errorMessage?: string }> = [];\n\n if (result.Records) {\n for (const r of result.Records) {\n const record = r as { ShardId?: string; SequenceNumber?: string; ErrorCode?: string; ErrorMessage?: string };\n if (record.ErrorCode) {\n failed.push({ errorCode: record.ErrorCode, errorMessage: record.ErrorMessage });\n } else {\n successful.push({ shardId: record.ShardId, sequenceNumber: record.SequenceNumber });\n }\n }\n }\n\n ctx.setAttribute('messaging.kinesis.successful_count', successful.length);\n ctx.setAttribute('messaging.kinesis.failed_count', result.FailedRecordCount || 0);\n\n if (result.FailedRecordCount && result.FailedRecordCount > 0) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: `${result.FailedRecordCount} records failed`,\n });\n } else {\n ctx.setStatus({ code: SpanStatusCode.OK });\n }\n\n return {\n successful,\n failed,\n failedRecordCount: result.FailedRecordCount || 0,\n };\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'Batch put failed',\n });\n throw error;\n }\n });\n }\n}\n\n// ============================================================================\n// Kinesis Consumer - Gets records with trace context extraction\n// ============================================================================\n\n/**\n * Configuration for Kinesis Consumer\n */\nexport interface KinesisConsumerConfig {\n /**\n * Kinesis stream name or ARN\n */\n streamName: string;\n\n /**\n * Extract W3C Trace Context from record data\n * Creates child spans linked to the producer\n * @default true\n */\n extractTraceContext?: boolean;\n\n /**\n * Optional service name for tracing\n */\n service?: string;\n}\n\n/**\n * Received Kinesis record with parsed data\n */\nexport interface ReceivedKinesisRecord {\n /**\n * Sequence number\n */\n sequenceNumber: string;\n\n /**\n * Approximate arrival timestamp\n */\n approximateArrivalTimestamp?: Date;\n\n /**\n * Parsed data (JSON parsed if possible)\n */\n \n data: any;\n\n /**\n * Raw data as string\n */\n rawData: string;\n\n /**\n * Partition key\n */\n partitionKey: string;\n\n /**\n * Encryption type\n */\n encryptionType?: string;\n\n /**\n * Original AWS SDK record object\n */\n \n raw: any;\n}\n\n/**\n * Record processor function type\n */\nexport type KinesisRecordProcessor = (\n record: ReceivedKinesisRecord,\n ctx: TraceContext,\n) => Promise<void>;\n\n/**\n * Kinesis Consumer with automatic trace context extraction\n *\n * Wraps a Kinesis client to automatically:\n * - Create spans for get operations\n * - Extract W3C Trace Context from record data\n * - Link consumer spans to producer spans\n *\n * @example Basic usage\n * ```typescript\n * import { KinesisConsumer } from 'autotel-aws/kinesis';\n * import { KinesisClient } from '@aws-sdk/client-kinesis';\n *\n * const kinesis = new KinesisClient({ region: 'us-east-1' });\n * const consumer = new KinesisConsumer(kinesis, {\n * streamName: 'my-stream'\n * });\n *\n * // Get shard iterator first\n * const iterator = await consumer.getShardIterator('shardId-000000000000', 'LATEST');\n *\n * // Process records with automatic tracing\n * const { nextIterator, records } = await consumer.getRecords(iterator, 100);\n *\n * for (const record of records) {\n * console.log('Record:', record.data);\n * }\n * ```\n *\n * @example With processor function\n * ```typescript\n * await consumer.processRecords(iterator, async (record, ctx) => {\n * ctx.setAttribute('event.type', record.data.event);\n * await handleEvent(record.data);\n * });\n * ```\n */\nexport class KinesisConsumer<\n \n TClient extends { send: (command: any) => Promise<any> } = any,\n> {\n private client: TClient;\n private config: Required<Pick<KinesisConsumerConfig, 'streamName'>> & KinesisConsumerConfig;\n\n constructor(client: TClient, config: KinesisConsumerConfig) {\n this.client = wrapSDKClient(client as any, config.service) as TClient;\n this.config = {\n extractTraceContext: true,\n ...config,\n };\n }\n\n /**\n * Extract trace context from record data\n */\n \n private extractContext(data: any): Record<string, string> | undefined {\n if (!this.config.extractTraceContext || !data?._traceContext) {\n return undefined;\n }\n\n const tc = data._traceContext;\n const carrier: Record<string, string> = {};\n\n if (tc.traceparent) carrier.traceparent = tc.traceparent;\n if (tc.tracestate) carrier.tracestate = tc.tracestate;\n if (tc.baggage) carrier.baggage = tc.baggage;\n\n return Object.keys(carrier).length > 0 ? carrier : undefined;\n }\n\n /**\n * Parse raw record data\n */\n \n private parseRecord(record: any): ReceivedKinesisRecord {\n const rawData = record.Data ? Buffer.from(record.Data).toString('utf8') : '';\n \n let data: any;\n\n try {\n data = JSON.parse(rawData);\n } catch {\n data = rawData;\n }\n\n return {\n sequenceNumber: record.SequenceNumber || '',\n approximateArrivalTimestamp: record.ApproximateArrivalTimestamp,\n data,\n rawData,\n partitionKey: record.PartitionKey || '',\n encryptionType: record.EncryptionType,\n raw: record,\n };\n }\n\n /**\n * Get a shard iterator\n *\n * @param shardId - Shard ID\n * @param type - Iterator type\n * @param startingSequenceNumber - Starting sequence number (for AT_SEQUENCE_NUMBER, AFTER_SEQUENCE_NUMBER)\n * @param timestamp - Starting timestamp (for AT_TIMESTAMP)\n * @returns Shard iterator string\n */\n async getShardIterator(\n shardId: string,\n type: 'AT_SEQUENCE_NUMBER' | 'AFTER_SEQUENCE_NUMBER' | 'TRIM_HORIZON' | 'LATEST' | 'AT_TIMESTAMP',\n startingSequenceNumber?: string,\n timestamp?: Date,\n ): Promise<string> {\n return trace(`kinesis.getShardIterator`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n shardId,\n operation: 'get',\n }),\n );\n\n try {\n const { GetShardIteratorCommand } = await import('@aws-sdk/client-kinesis');\n const result = await this.client.send(\n new GetShardIteratorCommand({\n StreamName: this.config.streamName,\n ShardId: shardId,\n ShardIteratorType: type,\n ...(startingSequenceNumber && { StartingSequenceNumber: startingSequenceNumber }),\n ...(timestamp && { Timestamp: timestamp }),\n }),\n );\n\n ctx.setStatus({ code: SpanStatusCode.OK });\n return result.ShardIterator || '';\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'GetShardIterator failed',\n });\n throw error;\n }\n });\n }\n\n /**\n * Get records from a shard iterator\n *\n * @param shardIterator - Shard iterator\n * @param limit - Maximum records to return (max 10000)\n * @returns Records and next shard iterator\n */\n async getRecords(\n shardIterator: string,\n limit?: number,\n ): Promise<{\n records: ReceivedKinesisRecord[];\n nextIterator?: string;\n millisBehindLatest?: number;\n }> {\n return trace(`kinesis.get`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n operation: 'get',\n }),\n );\n\n try {\n const { GetRecordsCommand } = await import('@aws-sdk/client-kinesis');\n const result = await this.client.send(\n new GetRecordsCommand({\n ShardIterator: shardIterator,\n ...(limit && { Limit: limit }),\n }),\n );\n\n \n const records = (result.Records || []).map((r: any) => this.parseRecord(r));\n ctx.setAttribute('messaging.batch.message_count', records.length);\n\n if (result.MillisBehindLatest !== undefined) {\n ctx.setAttribute('aws.kinesis.millis_behind_latest', result.MillisBehindLatest);\n }\n\n ctx.setStatus({ code: SpanStatusCode.OK });\n\n return {\n records,\n nextIterator: result.NextShardIterator,\n millisBehindLatest: result.MillisBehindLatest,\n };\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'GetRecords failed',\n });\n throw error;\n }\n });\n }\n\n /**\n * Process records with automatic trace context extraction\n *\n * @param shardIterator - Shard iterator\n * @param processor - Function to process each record\n * @param limit - Maximum records to process\n * @returns Next shard iterator and count of processed records\n */\n async processRecords(\n shardIterator: string,\n processor: KinesisRecordProcessor,\n limit?: number,\n ): Promise<{ nextIterator?: string; processedCount: number }> {\n const { records, nextIterator } = await this.getRecords(shardIterator, limit);\n let processedCount = 0;\n\n for (const record of records) {\n // Extract trace context from record data\n const carrier = this.extractContext(record.data);\n\n // Create processing span, optionally linked to producer\n const processRecord = async () => {\n return trace(`kinesis.process`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n operation: 'get',\n }),\n );\n ctx.setAttribute('aws.kinesis.sequence_number', record.sequenceNumber);\n ctx.setAttribute('aws.kinesis.partition_key', record.partitionKey);\n\n try {\n await processor(record, ctx);\n processedCount++;\n ctx.setStatus({ code: SpanStatusCode.OK });\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'Processing failed',\n });\n throw error;\n }\n });\n };\n\n // Run with extracted context if available\n if (carrier) {\n const extractedContext = propagation.extract(context.active(), carrier);\n await context.with(extractedContext, processRecord);\n } else {\n await processRecord();\n }\n }\n\n return { nextIterator, processedCount };\n }\n\n /**\n * List shards for the stream\n *\n * @returns Array of shard IDs\n */\n async listShards(): Promise<string[]> {\n return trace(`kinesis.listShards`, async (ctx: TraceContext) => {\n ctx.setAttributes(\n buildKinesisAttributes({\n streamName: this.config.streamName,\n operation: 'get',\n }),\n );\n\n try {\n const { ListShardsCommand } = await import('@aws-sdk/client-kinesis');\n const result = await this.client.send(\n new ListShardsCommand({\n StreamName: this.config.streamName,\n }),\n );\n\n const shardIds = result.Shards?.map((s: { ShardId?: string }) => s.ShardId || '') || [];\n ctx.setAttribute('aws.kinesis.shard_count', shardIds.length);\n ctx.setStatus({ code: SpanStatusCode.OK });\n\n return shardIds;\n } catch (error) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: error instanceof Error ? error.message : 'ListShards failed',\n });\n throw error;\n }\n });\n }\n}\n"]}
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
import { buildSDKAttributes } from './chunk-I4CKQ4RD.js';
|
|
2
|
+
import { trace } from 'autotel';
|
|
3
|
+
import { SpanStatusCode } from '@opentelemetry/api';
|
|
4
|
+
|
|
5
|
+
// src/common/error-handlers.ts
|
|
6
|
+
function classifyAWSError(error) {
|
|
7
|
+
if (!error || typeof error !== "object") {
|
|
8
|
+
return { isError: false };
|
|
9
|
+
}
|
|
10
|
+
const awsError = error;
|
|
11
|
+
const statusCode = awsError.$metadata?.httpStatusCode || awsError.StatusCode;
|
|
12
|
+
const isError = statusCode !== void 0 && statusCode >= 400;
|
|
13
|
+
return {
|
|
14
|
+
isError,
|
|
15
|
+
statusCode,
|
|
16
|
+
errorCode: awsError.Code || awsError.name
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
function extractErrorAttributes(error) {
|
|
20
|
+
if (!error || typeof error !== "object") {
|
|
21
|
+
return {};
|
|
22
|
+
}
|
|
23
|
+
const awsError = error;
|
|
24
|
+
const attrs = {};
|
|
25
|
+
if (awsError.name) {
|
|
26
|
+
attrs["error.type"] = awsError.name;
|
|
27
|
+
}
|
|
28
|
+
if (awsError.message) {
|
|
29
|
+
attrs["error.message"] = awsError.message;
|
|
30
|
+
}
|
|
31
|
+
if (awsError.Code) {
|
|
32
|
+
attrs["aws.error.code"] = awsError.Code;
|
|
33
|
+
}
|
|
34
|
+
if (awsError.$metadata?.requestId) {
|
|
35
|
+
attrs["aws.request_id"] = awsError.$metadata.requestId;
|
|
36
|
+
}
|
|
37
|
+
if (awsError.$metadata?.httpStatusCode) {
|
|
38
|
+
attrs["http.status_code"] = awsError.$metadata.httpStatusCode;
|
|
39
|
+
}
|
|
40
|
+
return attrs;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
// src/common/request-builder.ts
|
|
44
|
+
function extractRequestMetadata(command, context) {
|
|
45
|
+
return {
|
|
46
|
+
clientName: context.clientName,
|
|
47
|
+
commandName: command.constructor.name
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
function extractServiceName(clientName) {
|
|
51
|
+
return clientName.replace(/Client$/, "");
|
|
52
|
+
}
|
|
53
|
+
function extractOperationName(commandName) {
|
|
54
|
+
return commandName.replace(/Command$/, "");
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
// src/common/response-builder.ts
|
|
58
|
+
function extractResponseMetadata(response) {
|
|
59
|
+
const metadata = response.$metadata || {};
|
|
60
|
+
return {
|
|
61
|
+
requestId: metadata.requestId,
|
|
62
|
+
httpStatusCode: metadata.httpStatusCode,
|
|
63
|
+
extendedRequestId: metadata.extendedRequestId,
|
|
64
|
+
cfId: metadata.cfId
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
function wrapSDKClient(client, serviceName) {
|
|
68
|
+
const clientName = client.constructor.name;
|
|
69
|
+
const resolvedServiceName = serviceName || extractServiceName(clientName);
|
|
70
|
+
return new Proxy(client, {
|
|
71
|
+
get(target, prop) {
|
|
72
|
+
if (prop === "send") {
|
|
73
|
+
return async function tracedSend(command) {
|
|
74
|
+
const metadata = extractRequestMetadata(command, { clientName });
|
|
75
|
+
const operationName = extractOperationName(metadata.commandName);
|
|
76
|
+
return trace(`aws.${resolvedServiceName}.${operationName}`, async (ctx) => {
|
|
77
|
+
ctx.setAttributes(
|
|
78
|
+
buildSDKAttributes({
|
|
79
|
+
service: resolvedServiceName,
|
|
80
|
+
operation: operationName
|
|
81
|
+
})
|
|
82
|
+
);
|
|
83
|
+
try {
|
|
84
|
+
const response = await target.send(command);
|
|
85
|
+
const responseMetadata = extractResponseMetadata(response);
|
|
86
|
+
if (responseMetadata.requestId) {
|
|
87
|
+
ctx.setAttribute("aws.request_id", responseMetadata.requestId);
|
|
88
|
+
}
|
|
89
|
+
if (responseMetadata.httpStatusCode) {
|
|
90
|
+
ctx.setAttribute("http.status_code", responseMetadata.httpStatusCode);
|
|
91
|
+
}
|
|
92
|
+
if (responseMetadata.extendedRequestId) {
|
|
93
|
+
ctx.setAttribute("aws.extended_request_id", responseMetadata.extendedRequestId);
|
|
94
|
+
}
|
|
95
|
+
if (responseMetadata.cfId) {
|
|
96
|
+
ctx.setAttribute("aws.cf_id", responseMetadata.cfId);
|
|
97
|
+
}
|
|
98
|
+
if (responseMetadata.httpStatusCode) {
|
|
99
|
+
if (responseMetadata.httpStatusCode >= 400) {
|
|
100
|
+
ctx.setStatus({
|
|
101
|
+
code: SpanStatusCode.ERROR,
|
|
102
|
+
message: `HTTP ${responseMetadata.httpStatusCode}`
|
|
103
|
+
});
|
|
104
|
+
} else {
|
|
105
|
+
ctx.setStatus({ code: SpanStatusCode.OK });
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
return response;
|
|
109
|
+
} catch (error) {
|
|
110
|
+
const errorInfo = classifyAWSError(error);
|
|
111
|
+
const errorAttrs = extractErrorAttributes(error);
|
|
112
|
+
ctx.setAttributes(errorAttrs);
|
|
113
|
+
if (errorInfo.isError) {
|
|
114
|
+
ctx.setStatus({
|
|
115
|
+
code: SpanStatusCode.ERROR,
|
|
116
|
+
message: errorInfo.errorCode || "AWS Error"
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
throw error;
|
|
120
|
+
}
|
|
121
|
+
});
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
return target[prop];
|
|
125
|
+
}
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
export { classifyAWSError, extractErrorAttributes, extractOperationName, extractRequestMetadata, extractResponseMetadata, extractServiceName, wrapSDKClient };
|
|
130
|
+
//# sourceMappingURL=chunk-YG56NRIO.js.map
|
|
131
|
+
//# sourceMappingURL=chunk-YG56NRIO.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/common/error-handlers.ts","../src/common/request-builder.ts","../src/common/response-builder.ts","../src/common/sdk-wrapper.ts"],"names":[],"mappings":";;;;;AAqBO,SAAS,iBAAiB,KAAA,EAI/B;AACA,EAAA,IAAI,CAAC,KAAA,IAAS,OAAO,KAAA,KAAU,QAAA,EAAU;AACvC,IAAA,OAAO,EAAE,SAAS,KAAA,EAAM;AAAA,EAC1B;AAEA,EAAA,MAAM,QAAA,GAAW,KAAA;AAGjB,EAAA,MAAM,UAAA,GAAa,QAAA,CAAS,SAAA,EAAW,cAAA,IAAkB,QAAA,CAAS,UAAA;AAGlE,EAAA,MAAM,OAAA,GAAU,UAAA,KAAe,MAAA,IAAa,UAAA,IAAc,GAAA;AAE1D,EAAA,OAAO;AAAA,IACL,OAAA;AAAA,IACA,UAAA;AAAA,IACA,SAAA,EAAW,QAAA,CAAS,IAAA,IAAQ,QAAA,CAAS;AAAA,GACvC;AACF;AAKO,SAAS,uBAAuB,KAAA,EAAiD;AACtF,EAAA,IAAI,CAAC,KAAA,IAAS,OAAO,KAAA,KAAU,QAAA,EAAU;AACvC,IAAA,OAAO,EAAC;AAAA,EACV;AAEA,EAAA,MAAM,QAAA,GAAW,KAAA;AACjB,EAAA,MAAM,QAAyC,EAAC;AAEhD,EAAA,IAAI,SAAS,IAAA,EAAM;AACjB,IAAA,KAAA,CAAM,YAAY,IAAI,QAAA,CAAS,IAAA;AAAA,EACjC;AAEA,EAAA,IAAI,SAAS,OAAA,EAAS;AACpB,IAAA,KAAA,CAAM,eAAe,IAAI,QAAA,CAAS,OAAA;AAAA,EACpC;AAEA,EAAA,IAAI,SAAS,IAAA,EAAM;AACjB,IAAA,KAAA,CAAM,gBAAgB,IAAI,QAAA,CAAS,IAAA;AAAA,EACrC;AAEA,EAAA,IAAI,QAAA,CAAS,WAAW,SAAA,EAAW;AACjC,IAAA,KAAA,CAAM,gBAAgB,CAAA,GAAI,QAAA,CAAS,SAAA,CAAU,SAAA;AAAA,EAC/C;AAEA,EAAA,IAAI,QAAA,CAAS,WAAW,cAAA,EAAgB;AACtC,IAAA,KAAA,CAAM,kBAAkB,CAAA,GAAI,QAAA,CAAS,SAAA,CAAU,cAAA;AAAA,EACjD;AAEA,EAAA,OAAO,KAAA;AACT;;;ACpEO,SAAS,sBAAA,CACd,SACA,OAAA,EACoB;AACpB,EAAA,OAAO;AAAA,IACL,YAAY,OAAA,CAAQ,UAAA;AAAA,IACpB,WAAA,EAAa,QAAQ,WAAA,CAAY;AAAA,GACnC;AACF;AAKO,SAAS,mBAAmB,UAAA,EAA4B;AAE7D,EAAA,OAAO,UAAA,CAAW,OAAA,CAAQ,SAAA,EAAW,EAAE,CAAA;AACzC;AAKO,SAAS,qBAAqB,WAAA,EAA6B;AAEhE,EAAA,OAAO,WAAA,CAAY,OAAA,CAAQ,UAAA,EAAY,EAAE,CAAA;AAC3C;;;ACxBO,SAAS,wBACd,QAAA,EAC6B;AAC7B,EAAA,MAAM,QAAA,GAAW,QAAA,CAAS,SAAA,IAAa,EAAC;AACxC,EAAA,OAAO;AAAA,IACL,WAAW,QAAA,CAAS,SAAA;AAAA,IACpB,gBAAgB,QAAA,CAAS,cAAA;AAAA,IACzB,mBAAmB,QAAA,CAAS,iBAAA;AAAA,IAC5B,MAAM,QAAA,CAAS;AAAA,GACjB;AACF;ACFO,SAAS,aAAA,CACd,QACA,WAAA,EACG;AACH,EAAA,MAAM,UAAA,GAAc,OAAO,WAAA,CAAiC,IAAA;AAC5D,EAAA,MAAM,mBAAA,GAAsB,WAAA,IAAe,kBAAA,CAAmB,UAAU,CAAA;AAGxE,EAAA,OAAO,IAAI,MAAM,MAAA,EAAQ;AAAA,IACvB,GAAA,CAAI,QAAQ,IAAA,EAAM;AAChB,MAAA,IAAI,SAAS,MAAA,EAAQ;AACnB,QAAA,OAAO,eAAe,WAAW,OAAA,EAA2C;AAC1E,UAAA,MAAM,QAAA,GAAW,sBAAA,CAAuB,OAAA,EAAS,EAAE,YAAY,CAAA;AAC/D,UAAA,MAAM,aAAA,GAAgB,oBAAA,CAAqB,QAAA,CAAS,WAAW,CAAA;AAE/D,UAAA,OAAO,MAAM,CAAA,IAAA,EAAO,mBAAmB,IAAI,aAAa,CAAA,CAAA,EAAI,OAAO,GAAA,KAAQ;AAEzE,YAAA,GAAA,CAAI,aAAA;AAAA,cACF,kBAAA,CAAmB;AAAA,gBACjB,OAAA,EAAS,mBAAA;AAAA,gBACT,SAAA,EAAW;AAAA,eACZ;AAAA,aACH;AAEA,YAAA,IAAI;AACF,cAAA,MAAM,QAAA,GAAW,MAAM,MAAA,CAAO,IAAA,CAAK,OAAO,CAAA;AAG1C,cAAA,MAAM,gBAAA,GAAmB,wBAAwB,QAAQ,CAAA;AACzD,cAAA,IAAI,iBAAiB,SAAA,EAAW;AAC9B,gBAAA,GAAA,CAAI,YAAA,CAAa,gBAAA,EAAkB,gBAAA,CAAiB,SAAS,CAAA;AAAA,cAC/D;AACA,cAAA,IAAI,iBAAiB,cAAA,EAAgB;AACnC,gBAAA,GAAA,CAAI,YAAA,CAAa,kBAAA,EAAoB,gBAAA,CAAiB,cAAc,CAAA;AAAA,cACtE;AACA,cAAA,IAAI,iBAAiB,iBAAA,EAAmB;AACtC,gBAAA,GAAA,CAAI,YAAA,CAAa,yBAAA,EAA2B,gBAAA,CAAiB,iBAAiB,CAAA;AAAA,cAChF;AACA,cAAA,IAAI,iBAAiB,IAAA,EAAM;AACzB,gBAAA,GAAA,CAAI,YAAA,CAAa,WAAA,EAAa,gBAAA,CAAiB,IAAI,CAAA;AAAA,cACrD;AAGA,cAAA,IAAI,iBAAiB,cAAA,EAAgB;AACnC,gBAAA,IAAI,gBAAA,CAAiB,kBAAkB,GAAA,EAAK;AAC1C,kBAAA,GAAA,CAAI,SAAA,CAAU;AAAA,oBACZ,MAAM,cAAA,CAAe,KAAA;AAAA,oBACrB,OAAA,EAAS,CAAA,KAAA,EAAQ,gBAAA,CAAiB,cAAc,CAAA;AAAA,mBACjD,CAAA;AAAA,gBACH,CAAA,MAAO;AACL,kBAAA,GAAA,CAAI,SAAA,CAAU,EAAE,IAAA,EAAM,cAAA,CAAe,IAAI,CAAA;AAAA,gBAC3C;AAAA,cACF;AAEA,cAAA,OAAO,QAAA;AAAA,YACT,SAAS,KAAA,EAAO;AAEd,cAAA,MAAM,SAAA,GAAY,iBAAiB,KAAK,CAAA;AACxC,cAAA,MAAM,UAAA,GAAa,uBAAuB,KAAK,CAAA;AAE/C,cAAA,GAAA,CAAI,cAAc,UAAU,CAAA;AAE5B,cAAA,IAAI,UAAU,OAAA,EAAS;AACrB,gBAAA,GAAA,CAAI,SAAA,CAAU;AAAA,kBACZ,MAAM,cAAA,CAAe,KAAA;AAAA,kBACrB,OAAA,EAAS,UAAU,SAAA,IAAa;AAAA,iBACjC,CAAA;AAAA,cACH;AAEA,cAAA,MAAM,KAAA;AAAA,YACR;AAAA,UACF,CAAC,CAAA;AAAA,QACH,CAAA;AAAA,MACF;AAEA,MAAA,OAAQ,OAAe,IAAI,CAAA;AAAA,IAC7B;AAAA,GACD,CAAA;AACH","file":"chunk-YG56NRIO.js","sourcesContent":["/**\n * AWS error classification and handling\n */\n\n/**\n * AWS error types\n */\nexport interface AWSError {\n name: string;\n message: string;\n $metadata?: {\n httpStatusCode?: number;\n requestId?: string;\n };\n Code?: string;\n StatusCode?: number;\n}\n\n/**\n * Classify AWS error for span status\n */\nexport function classifyAWSError(error: unknown): {\n isError: boolean;\n statusCode?: number;\n errorCode?: string;\n} {\n if (!error || typeof error !== 'object') {\n return { isError: false };\n }\n\n const awsError = error as AWSError;\n\n // Check for HTTP status code\n const statusCode = awsError.$metadata?.httpStatusCode || awsError.StatusCode;\n\n // Determine if it's an error (4xx or 5xx)\n const isError = statusCode !== undefined && statusCode >= 400;\n\n return {\n isError,\n statusCode,\n errorCode: awsError.Code || awsError.name,\n };\n}\n\n/**\n * Extract error attributes from AWS error\n */\nexport function extractErrorAttributes(error: unknown): Record<string, string | number> {\n if (!error || typeof error !== 'object') {\n return {};\n }\n\n const awsError = error as AWSError;\n const attrs: Record<string, string | number> = {};\n\n if (awsError.name) {\n attrs['error.type'] = awsError.name;\n }\n\n if (awsError.message) {\n attrs['error.message'] = awsError.message;\n }\n\n if (awsError.Code) {\n attrs['aws.error.code'] = awsError.Code;\n }\n\n if (awsError.$metadata?.requestId) {\n attrs['aws.request_id'] = awsError.$metadata.requestId;\n }\n\n if (awsError.$metadata?.httpStatusCode) {\n attrs['http.status_code'] = awsError.$metadata.httpStatusCode;\n }\n\n return attrs;\n}\n","/**\n * Request metadata extraction utilities\n */\n\nimport type { AWSCommandMetadata } from '../types';\n\n/**\n * Extract request metadata from AWS SDK v3 command\n */\nexport function extractRequestMetadata(\n command: { constructor: { name: string } },\n context: { clientName: string }\n): AWSCommandMetadata {\n return {\n clientName: context.clientName,\n commandName: command.constructor.name,\n };\n}\n\n/**\n * Extract service name from AWS SDK client\n */\nexport function extractServiceName(clientName: string): string {\n // Remove \"Client\" suffix if present\n return clientName.replace(/Client$/, '');\n}\n\n/**\n * Extract operation name from command\n */\nexport function extractOperationName(commandName: string): string {\n // Remove \"Command\" suffix if present\n return commandName.replace(/Command$/, '');\n}\n","/**\n * Response metadata extraction utilities\n */\n\nimport type { AWSCommandMetadata } from '../types';\n\n/**\n * Extract response metadata from AWS SDK v3 response\n */\nexport function extractResponseMetadata(\n response: { $metadata?: Record<string, unknown> }\n): Partial<AWSCommandMetadata> {\n const metadata = response.$metadata || {};\n return {\n requestId: metadata.requestId as string | undefined,\n httpStatusCode: metadata.httpStatusCode as number | undefined,\n extendedRequestId: metadata.extendedRequestId as string | undefined,\n cfId: metadata.cfId as string | undefined,\n };\n}\n","/**\n * Generic AWS SDK v3 client wrapper utilities\n */\n\n// Type-only imports from optional peer dependencies\n// @ts-expect-error - Optional peer dependency, may not be installed\nimport type { Client, Command } from '@aws-sdk/smithy-client';\nimport { extractRequestMetadata, extractServiceName, extractOperationName } from './request-builder';\nimport { extractResponseMetadata } from './response-builder';\nimport { classifyAWSError, extractErrorAttributes } from './error-handlers';\nimport { buildSDKAttributes } from '../attributes';\nimport { trace } from 'autotel';\nimport { SpanStatusCode } from '@opentelemetry/api';\n\n/**\n * Wrap AWS SDK v3 client with OpenTelemetry instrumentation\n */\nexport function wrapSDKClient<T extends Client<any, any, any, any>>(\n client: T,\n serviceName?: string\n): T {\n const clientName = (client.constructor as { name: string }).name;\n const resolvedServiceName = serviceName || extractServiceName(clientName);\n\n // Create a proxy that intercepts send() calls\n return new Proxy(client, {\n get(target, prop) {\n if (prop === 'send') {\n return async function tracedSend(command: Command<any, any, any, any, any>) {\n const metadata = extractRequestMetadata(command, { clientName });\n const operationName = extractOperationName(metadata.commandName);\n\n return trace(`aws.${resolvedServiceName}.${operationName}`, async (ctx) => {\n // Set request attributes\n ctx.setAttributes(\n buildSDKAttributes({\n service: resolvedServiceName,\n operation: operationName,\n })\n );\n\n try {\n const response = await target.send(command);\n\n // Extract and set response metadata\n const responseMetadata = extractResponseMetadata(response);\n if (responseMetadata.requestId) {\n ctx.setAttribute('aws.request_id', responseMetadata.requestId);\n }\n if (responseMetadata.httpStatusCode) {\n ctx.setAttribute('http.status_code', responseMetadata.httpStatusCode);\n }\n if (responseMetadata.extendedRequestId) {\n ctx.setAttribute('aws.extended_request_id', responseMetadata.extendedRequestId);\n }\n if (responseMetadata.cfId) {\n ctx.setAttribute('aws.cf_id', responseMetadata.cfId);\n }\n\n // Set span status based on HTTP status code\n if (responseMetadata.httpStatusCode) {\n if (responseMetadata.httpStatusCode >= 400) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: `HTTP ${responseMetadata.httpStatusCode}`,\n });\n } else {\n ctx.setStatus({ code: SpanStatusCode.OK });\n }\n }\n\n return response;\n } catch (error) {\n // Classify and handle error\n const errorInfo = classifyAWSError(error);\n const errorAttrs = extractErrorAttributes(error);\n\n ctx.setAttributes(errorAttrs);\n\n if (errorInfo.isError) {\n ctx.setStatus({\n code: SpanStatusCode.ERROR,\n message: errorInfo.errorCode || 'AWS Error',\n });\n }\n\n throw error;\n }\n });\n };\n }\n\n return (target as any)[prop];\n },\n }) as T;\n}\n"]}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { buildS3Attributes } from './chunk-I4CKQ4RD.js';
|
|
2
|
+
import { trace } from 'autotel';
|
|
3
|
+
|
|
4
|
+
function traceS3(config) {
|
|
5
|
+
return function wrapper(fn) {
|
|
6
|
+
return trace(
|
|
7
|
+
`s3.${config.operation}`,
|
|
8
|
+
(ctx) => async (...args) => {
|
|
9
|
+
if (config.bucket) {
|
|
10
|
+
ctx.setAttributes(buildS3Attributes({ bucket: config.bucket }));
|
|
11
|
+
}
|
|
12
|
+
const handler = fn(ctx);
|
|
13
|
+
return handler(...args);
|
|
14
|
+
}
|
|
15
|
+
);
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
export { traceS3 };
|
|
20
|
+
//# sourceMappingURL=chunk-ZPDRKCAR.js.map
|
|
21
|
+
//# sourceMappingURL=chunk-ZPDRKCAR.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/s3/index.ts"],"names":[],"mappings":";;;AA6EO,SAAS,QAAQ,MAAA,EAAuB;AAC7C,EAAA,OAAO,SAAS,QACd,EAAA,EACsC;AAEtC,IAAA,OAAO,KAAA;AAAA,MACL,CAAA,GAAA,EAAM,OAAO,SAAS,CAAA,CAAA;AAAA,MACtB,CAAC,GAAA,KACC,OAAA,GAAU,IAAA,KAAkC;AAE1C,QAAA,IAAI,OAAO,MAAA,EAAQ;AACjB,UAAA,GAAA,CAAI,cAAc,iBAAA,CAAkB,EAAE,QAAQ,MAAA,CAAO,MAAA,EAAQ,CAAC,CAAA;AAAA,QAChE;AAGA,QAAA,MAAM,OAAA,GAAU,GAAG,GAAG,CAAA;AACtB,QAAA,OAAO,OAAA,CAAQ,GAAG,IAAI,CAAA;AAAA,MACxB;AAAA,KACJ;AAAA,EACF,CAAA;AACF","file":"chunk-ZPDRKCAR.js","sourcesContent":["/**\n * S3-specific instrumentation\n *\n * Provides semantic helpers for tracing S3 operations with proper OpenTelemetry\n * semantic conventions. Automatically sets `aws.s3.*` attributes.\n *\n * @example Basic usage with factory pattern\n * ```typescript\n * import { traceS3 } from 'autotel-aws/s3';\n * import { S3Client, GetObjectCommand } from '@aws-sdk/client-s3';\n *\n * const s3 = new S3Client({});\n *\n * export const getFile = traceS3({\n * operation: 'GetObject',\n * bucket: 'my-bucket'\n * })(ctx => async (key: string) => {\n * ctx.setAttribute('aws.s3.key', key);\n * return await s3.send(new GetObjectCommand({ Bucket: 'my-bucket', Key: key }));\n * });\n *\n * // Usage: await getFile('path/to/file.txt');\n * ```\n *\n * @example Dynamic bucket\n * ```typescript\n * export const getObject = traceS3({\n * operation: 'GetObject',\n * })(ctx => async (bucket: string, key: string) => {\n * ctx.setAttribute('aws.s3.bucket', bucket);\n * ctx.setAttribute('aws.s3.key', key);\n * return await s3.send(new GetObjectCommand({ Bucket: bucket, Key: key }));\n * });\n *\n * // Usage: await getObject('my-bucket', 'file.txt');\n * ```\n */\n\nimport { trace, type TraceContext } from 'autotel';\nimport { buildS3Attributes } from '../attributes';\n\n/**\n * S3 operation configuration\n */\nexport interface TraceS3Config {\n /**\n * S3 operation name (e.g., 'GetObject', 'PutObject', 'DeleteObject')\n * Used to generate the span name: `s3.{operation}`\n */\n operation: string;\n\n /**\n * Default bucket name for static configurations.\n * Can be overridden by setting `aws.s3.bucket` attribute in the handler.\n */\n bucket?: string;\n}\n\n/**\n * Trace S3 operations with semantic attributes\n *\n * Creates a traced function that automatically sets S3 semantic attributes\n * following OpenTelemetry conventions.\n *\n * @param config - S3 operation configuration\n * @returns A higher-order function that wraps your S3 operation with tracing\n *\n * @remarks\n * Semantic attributes set automatically:\n * - `aws.s3.bucket` - S3 bucket name (if provided in config)\n *\n * Additional attributes you should set in your handler:\n * - `aws.s3.key` - Object key\n * - `aws.s3.copy_source` - Source for copy operations\n *\n * @see https://opentelemetry.io/docs/specs/semconv/object-stores/s3/\n */\nexport function traceS3(config: TraceS3Config) {\n return function wrapper<TArgs extends unknown[], TReturn>(\n fn: (ctx: TraceContext) => (...args: TArgs) => Promise<TReturn>,\n ): (...args: TArgs) => Promise<TReturn> {\n // Use autotel's trace() which properly handles the factory pattern\n return trace(\n `s3.${config.operation}`,\n (ctx: TraceContext) =>\n async (...args: TArgs): Promise<TReturn> => {\n // Set S3 semantic attributes\n if (config.bucket) {\n ctx.setAttributes(buildS3Attributes({ bucket: config.bucket }));\n }\n\n // Get the user's handler and execute with forwarded arguments\n const handler = fn(ctx);\n return handler(...args);\n },\n );\n };\n}\n"]}
|