@paid-ai/paid-node 0.0.8-alpha1 → 0.0.8-alpha3
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.md +17 -16
- package/dist/cjs/Client.d.ts +3 -2
- package/dist/cjs/Client.js +12 -4
- package/dist/cjs/index.d.ts +3 -1
- package/dist/cjs/index.js +7 -4
- package/dist/cjs/tracing/signal.d.ts +1 -0
- package/dist/cjs/tracing/signal.js +45 -0
- package/dist/cjs/tracing/tracing.d.ts +7 -3
- package/dist/cjs/tracing/tracing.js +78 -31
- package/dist/cjs/tracing/wrappers/anthropicWrapper.d.ts +16 -0
- package/dist/cjs/tracing/wrappers/anthropicWrapper.js +84 -0
- package/dist/cjs/tracing/wrappers/langchainCallback.d.ts +21 -0
- package/dist/cjs/tracing/wrappers/langchainCallback.js +142 -0
- package/dist/cjs/tracing/wrappers/mistralWrapper.d.ts +17 -0
- package/dist/cjs/tracing/wrappers/mistralWrapper.js +81 -0
- package/dist/cjs/tracing/wrappers/openAiWrapper.js +42 -56
- package/dist/cjs/version.d.ts +1 -1
- package/dist/cjs/version.js +1 -1
- package/dist/cjs/wrapper/BatchUsage.d.ts +1 -1
- package/dist/cjs/wrapper/BatchUsage.js +2 -2
- package/dist/esm/Client.d.mts +3 -2
- package/dist/esm/Client.mjs +13 -5
- package/dist/esm/index.d.mts +3 -1
- package/dist/esm/index.mjs +3 -1
- package/dist/esm/tracing/signal.d.mts +1 -0
- package/dist/esm/tracing/signal.mjs +42 -0
- package/dist/esm/tracing/tracing.d.mts +7 -3
- package/dist/esm/tracing/tracing.mjs +73 -30
- package/dist/esm/tracing/wrappers/anthropicWrapper.d.mts +16 -0
- package/dist/esm/tracing/wrappers/anthropicWrapper.mjs +80 -0
- package/dist/esm/tracing/wrappers/langchainCallback.d.mts +21 -0
- package/dist/esm/tracing/wrappers/langchainCallback.mjs +138 -0
- package/dist/esm/tracing/wrappers/mistralWrapper.d.mts +17 -0
- package/dist/esm/tracing/wrappers/mistralWrapper.mjs +77 -0
- package/dist/esm/tracing/wrappers/openAiWrapper.mjs +42 -56
- package/dist/esm/version.d.mts +1 -1
- package/dist/esm/version.mjs +1 -1
- package/dist/esm/wrapper/BatchUsage.d.mts +1 -1
- package/dist/esm/wrapper/BatchUsage.mjs +1 -1
- package/package.json +7 -3
- package/dist/cjs/tracing/index.d.ts +0 -1
- package/dist/cjs/tracing/index.js +0 -17
- package/dist/esm/tracing/index.d.mts +0 -1
- package/dist/esm/tracing/index.mjs +0 -1
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
5
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
6
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
7
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
8
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
|
+
});
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.PaidMistral = void 0;
|
|
13
|
+
const api_1 = require("@opentelemetry/api");
|
|
14
|
+
const tracing_js_1 = require("../tracing.js");
|
|
15
|
+
class PaidMistral {
|
|
16
|
+
constructor(mistralClient) {
|
|
17
|
+
this.mistral = mistralClient;
|
|
18
|
+
this.tracer = tracing_js_1.paidTracer;
|
|
19
|
+
}
|
|
20
|
+
get ocr() {
|
|
21
|
+
return new OCRWrapper(this.mistral, this.tracer);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
exports.PaidMistral = PaidMistral;
|
|
25
|
+
class OCRWrapper {
|
|
26
|
+
constructor(mistral, tracer) {
|
|
27
|
+
this.mistral = mistral;
|
|
28
|
+
this.tracer = tracer;
|
|
29
|
+
}
|
|
30
|
+
process(request, options) {
|
|
31
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
32
|
+
const externalCustomerId = (0, tracing_js_1.getCustomerIdStorage)();
|
|
33
|
+
const externalAgentId = (0, tracing_js_1.getAgentIdStorage)();
|
|
34
|
+
const token = (0, tracing_js_1.getTokenStorage)();
|
|
35
|
+
if (!token || !externalCustomerId) {
|
|
36
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
37
|
+
}
|
|
38
|
+
return this.tracer.startActiveSpan("trace.mistral.ocr", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
39
|
+
var _a;
|
|
40
|
+
const attributes = {
|
|
41
|
+
"gen_ai.system": "mistral",
|
|
42
|
+
"gen_ai.operation.name": "ocr",
|
|
43
|
+
external_customer_id: externalCustomerId,
|
|
44
|
+
token: token,
|
|
45
|
+
};
|
|
46
|
+
if (externalAgentId) {
|
|
47
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
48
|
+
}
|
|
49
|
+
// Check if annotations are requested
|
|
50
|
+
if (request.bboxAnnotationFormat || request.documentAnnotationFormat) {
|
|
51
|
+
attributes["gen_ai.ocr.annotated"] = "true";
|
|
52
|
+
}
|
|
53
|
+
// Set request model
|
|
54
|
+
if (request.model) {
|
|
55
|
+
attributes["gen_ai.request.model"] = request.model;
|
|
56
|
+
}
|
|
57
|
+
span.setAttributes(attributes);
|
|
58
|
+
try {
|
|
59
|
+
const response = yield this.mistral.ocr.process(request, options);
|
|
60
|
+
// Add usage information from response
|
|
61
|
+
if (((_a = response.usageInfo) === null || _a === void 0 ? void 0 : _a.pagesProcessed) !== undefined) {
|
|
62
|
+
span.setAttribute("gen_ai.ocr.pages_processed", response.usageInfo.pagesProcessed);
|
|
63
|
+
}
|
|
64
|
+
if (response.model) {
|
|
65
|
+
span.setAttribute("gen_ai.response.model", response.model);
|
|
66
|
+
}
|
|
67
|
+
span.setStatus({ code: api_1.SpanStatusCode.OK });
|
|
68
|
+
return response;
|
|
69
|
+
}
|
|
70
|
+
catch (error) {
|
|
71
|
+
span.setStatus({ code: api_1.SpanStatusCode.ERROR, message: error.message });
|
|
72
|
+
span.recordException(error);
|
|
73
|
+
throw error;
|
|
74
|
+
}
|
|
75
|
+
finally {
|
|
76
|
+
span.end();
|
|
77
|
+
}
|
|
78
|
+
}));
|
|
79
|
+
});
|
|
80
|
+
}
|
|
81
|
+
}
|
|
@@ -11,11 +11,11 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
11
11
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
12
|
exports.PaidOpenAI = void 0;
|
|
13
13
|
const api_1 = require("@opentelemetry/api");
|
|
14
|
-
const
|
|
14
|
+
const tracing_js_1 = require("../tracing.js");
|
|
15
15
|
class PaidOpenAI {
|
|
16
16
|
constructor(openaiClient) {
|
|
17
17
|
this.openai = openaiClient;
|
|
18
|
-
this.tracer =
|
|
18
|
+
this.tracer = tracing_js_1.paidTracer;
|
|
19
19
|
}
|
|
20
20
|
get chat() {
|
|
21
21
|
return new ChatWrapper(this.openai, this.tracer);
|
|
@@ -47,25 +47,21 @@ class ChatCompletionsWrapper {
|
|
|
47
47
|
}
|
|
48
48
|
create(params) {
|
|
49
49
|
return __awaiter(this, void 0, void 0, function* () {
|
|
50
|
-
const
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
50
|
+
const externalCustomerId = (0, tracing_js_1.getCustomerIdStorage)();
|
|
51
|
+
const externalAgentId = (0, tracing_js_1.getAgentIdStorage)();
|
|
52
|
+
const token = (0, tracing_js_1.getTokenStorage)();
|
|
53
|
+
if (!token || !externalCustomerId) {
|
|
54
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
54
55
|
}
|
|
55
|
-
|
|
56
|
-
const token = (0, tracing_1.getTokenStorage)();
|
|
57
|
-
const model = params.model;
|
|
58
|
-
const spanName = `trace.chat ${model}`;
|
|
59
|
-
return this.tracer.startActiveSpan(spanName, (span) => __awaiter(this, void 0, void 0, function* () {
|
|
56
|
+
return this.tracer.startActiveSpan("trace.openai.chat", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
60
57
|
const attributes = {
|
|
61
58
|
"gen_ai.system": "openai",
|
|
62
59
|
"gen_ai.operation.name": "chat",
|
|
63
60
|
};
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
attributes["token"] = token;
|
|
61
|
+
attributes["external_customer_id"] = externalCustomerId;
|
|
62
|
+
attributes["token"] = token;
|
|
63
|
+
if (externalAgentId) {
|
|
64
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
69
65
|
}
|
|
70
66
|
span.setAttributes(attributes);
|
|
71
67
|
try {
|
|
@@ -99,24 +95,22 @@ class ResponsesWrapper {
|
|
|
99
95
|
}
|
|
100
96
|
create(params) {
|
|
101
97
|
return __awaiter(this, void 0, void 0, function* () {
|
|
102
|
-
const
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
98
|
+
const externalCustomerId = (0, tracing_js_1.getCustomerIdStorage)();
|
|
99
|
+
const externalAgentId = (0, tracing_js_1.getAgentIdStorage)();
|
|
100
|
+
const token = (0, tracing_js_1.getTokenStorage)();
|
|
101
|
+
if (!token || !externalCustomerId) {
|
|
102
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
106
103
|
}
|
|
107
|
-
const externalCustomerId = (0, tracing_1.getCustomerId)();
|
|
108
|
-
const token = (0, tracing_1.getTokenStorage)();
|
|
109
104
|
return this.tracer.startActiveSpan("trace.openai.responses", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
110
105
|
var _a, _b;
|
|
111
106
|
const attributes = {
|
|
112
107
|
"gen_ai.system": "openai",
|
|
113
108
|
"gen_ai.operation.name": "chat", // Equivalent to chat.completions
|
|
114
109
|
};
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
attributes["token"] = token;
|
|
110
|
+
attributes["external_customer_id"] = externalCustomerId;
|
|
111
|
+
attributes["token"] = token;
|
|
112
|
+
if (externalAgentId) {
|
|
113
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
120
114
|
}
|
|
121
115
|
span.setAttributes(attributes);
|
|
122
116
|
try {
|
|
@@ -156,26 +150,21 @@ class EmbeddingsWrapper {
|
|
|
156
150
|
}
|
|
157
151
|
create(params) {
|
|
158
152
|
return __awaiter(this, void 0, void 0, function* () {
|
|
159
|
-
|
|
160
|
-
const
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
153
|
+
const externalCustomerId = (0, tracing_js_1.getCustomerIdStorage)();
|
|
154
|
+
const externalAgentId = (0, tracing_js_1.getAgentIdStorage)();
|
|
155
|
+
const token = (0, tracing_js_1.getTokenStorage)();
|
|
156
|
+
if (!token || !externalCustomerId) {
|
|
157
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
164
158
|
}
|
|
165
|
-
|
|
166
|
-
const token = (0, tracing_1.getTokenStorage)();
|
|
167
|
-
const model = (_a = params.model) !== null && _a !== void 0 ? _a : "unknown";
|
|
168
|
-
const spanName = `trace.embeddings ${model}`;
|
|
169
|
-
return this.tracer.startActiveSpan(spanName, (span) => __awaiter(this, void 0, void 0, function* () {
|
|
159
|
+
return this.tracer.startActiveSpan("trace.openai.embeddings", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
170
160
|
const attributes = {
|
|
171
161
|
"gen_ai.system": "openai",
|
|
172
162
|
"gen_ai.operation.name": "embeddings",
|
|
173
163
|
};
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
attributes["token"] = token;
|
|
164
|
+
attributes["external_customer_id"] = externalCustomerId;
|
|
165
|
+
attributes["token"] = token;
|
|
166
|
+
if (externalAgentId) {
|
|
167
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
179
168
|
}
|
|
180
169
|
span.setAttributes(attributes);
|
|
181
170
|
try {
|
|
@@ -209,27 +198,24 @@ class ImagesWrapper {
|
|
|
209
198
|
generate(params) {
|
|
210
199
|
return __awaiter(this, void 0, void 0, function* () {
|
|
211
200
|
var _a;
|
|
212
|
-
const
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
return this.openai.images.generate(params);
|
|
216
|
-
}
|
|
217
|
-
const externalCustomerId = (0, tracing_1.getCustomerId)();
|
|
218
|
-
const token = (0, tracing_1.getTokenStorage)();
|
|
201
|
+
const externalCustomerId = (0, tracing_js_1.getCustomerIdStorage)();
|
|
202
|
+
const externalAgentId = (0, tracing_js_1.getAgentIdStorage)();
|
|
203
|
+
const token = (0, tracing_js_1.getTokenStorage)();
|
|
219
204
|
const model = (_a = params.model) !== null && _a !== void 0 ? _a : "dall-e-3";
|
|
220
|
-
|
|
221
|
-
|
|
205
|
+
if (!token || !externalCustomerId) {
|
|
206
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
207
|
+
}
|
|
208
|
+
return this.tracer.startActiveSpan("trace.openai.images", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
222
209
|
var _a, _b, _c;
|
|
223
210
|
const attributes = {
|
|
224
211
|
"gen_ai.request.model": model,
|
|
225
212
|
"gen_ai.system": "openai",
|
|
226
213
|
"gen_ai.operation.name": "image_generation",
|
|
227
214
|
};
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
attributes["token"] = token;
|
|
215
|
+
attributes["external_customer_id"] = externalCustomerId;
|
|
216
|
+
attributes["token"] = token;
|
|
217
|
+
if (externalAgentId) {
|
|
218
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
233
219
|
}
|
|
234
220
|
span.setAttributes(attributes);
|
|
235
221
|
try {
|
package/dist/cjs/version.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const SDK_VERSION = "0.0.8-
|
|
1
|
+
export declare const SDK_VERSION = "0.0.8-alpha3";
|
package/dist/cjs/version.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as core from "../core/index.js";
|
|
2
|
-
import { Usage as UsageClient } from "../api/resources/usage/client/Client";
|
|
2
|
+
import { Usage as UsageClient } from "../api/resources/usage/client/Client.js";
|
|
3
3
|
import * as Paid from "../api/types/Signal.js";
|
|
4
4
|
export declare class Usage extends UsageClient {
|
|
5
5
|
private signals;
|
|
@@ -35,8 +35,8 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
35
35
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
36
|
exports.Usage = void 0;
|
|
37
37
|
const core = __importStar(require("../core/index.js"));
|
|
38
|
-
const
|
|
39
|
-
class Usage extends
|
|
38
|
+
const Client_js_1 = require("../api/resources/usage/client/Client.js");
|
|
39
|
+
class Usage extends Client_js_1.Usage {
|
|
40
40
|
constructor() {
|
|
41
41
|
super(...arguments);
|
|
42
42
|
this.signals = [];
|
package/dist/esm/Client.d.mts
CHANGED
|
@@ -41,6 +41,7 @@ export declare class PaidClient {
|
|
|
41
41
|
get contacts(): Contacts;
|
|
42
42
|
get orders(): Orders;
|
|
43
43
|
get usage(): Usage;
|
|
44
|
-
initializeTracing(): Promise<void>;
|
|
45
|
-
|
|
44
|
+
initializeTracing(collectorEndpoint?: string): Promise<void>;
|
|
45
|
+
trace<T extends (...args: any[]) => any>(externalCustomerId: string, fn: T, externalAgentId?: string, ...args: Parameters<T>): Promise<ReturnType<T>>;
|
|
46
|
+
signal(eventName: string, data?: Record<string, any>): void;
|
|
46
47
|
}
|
package/dist/esm/Client.mjs
CHANGED
|
@@ -17,7 +17,8 @@ import { Agents } from "./api/resources/agents/client/Client.mjs";
|
|
|
17
17
|
import { Contacts } from "./api/resources/contacts/client/Client.mjs";
|
|
18
18
|
import { Orders } from "./api/resources/orders/client/Client.mjs";
|
|
19
19
|
import { Usage } from "./wrapper/BatchUsage.mjs";
|
|
20
|
-
import {
|
|
20
|
+
import { _trace, _initializeTracing } from "./tracing/tracing.mjs";
|
|
21
|
+
import { _signal } from "./tracing/signal.mjs";
|
|
21
22
|
export class PaidClient {
|
|
22
23
|
constructor(_options) {
|
|
23
24
|
this._options = Object.assign(Object.assign({}, _options), { headers: mergeHeaders({
|
|
@@ -49,17 +50,24 @@ export class PaidClient {
|
|
|
49
50
|
var _a;
|
|
50
51
|
return ((_a = this._usage) !== null && _a !== void 0 ? _a : (this._usage = new Usage(this._options)));
|
|
51
52
|
}
|
|
52
|
-
|
|
53
|
+
// Need to call this method before using tracing or creating wrappers.
|
|
54
|
+
initializeTracing(collectorEndpoint) {
|
|
53
55
|
return __awaiter(this, void 0, void 0, function* () {
|
|
54
56
|
const tokenSupplier = this._options.token;
|
|
55
57
|
const token = typeof tokenSupplier === "function" ? yield tokenSupplier() : tokenSupplier;
|
|
56
58
|
const resolvedToken = yield Promise.resolve(token);
|
|
57
|
-
|
|
59
|
+
_initializeTracing(resolvedToken, collectorEndpoint);
|
|
58
60
|
});
|
|
59
61
|
}
|
|
60
|
-
|
|
62
|
+
// Use this method to track actions like LLM usage and sending signals.
|
|
63
|
+
// The callback to this function is the work that you want to trace.
|
|
64
|
+
trace(externalCustomerId, fn, externalAgentId, ...args) {
|
|
61
65
|
return __awaiter(this, void 0, void 0, function* () {
|
|
62
|
-
return yield
|
|
66
|
+
return yield _trace(externalCustomerId, fn, externalAgentId, ...args);
|
|
63
67
|
});
|
|
64
68
|
}
|
|
69
|
+
// sends Paid signal. This needs to called as part of callback to Paid.trace()
|
|
70
|
+
signal(eventName, data) {
|
|
71
|
+
return _signal(eventName, data);
|
|
72
|
+
}
|
|
65
73
|
}
|
package/dist/esm/index.d.mts
CHANGED
|
@@ -3,4 +3,6 @@ export { PaidClient } from "./Client.mjs";
|
|
|
3
3
|
export { PaidError, PaidTimeoutError } from "./errors/index.mjs";
|
|
4
4
|
export { PaidEnvironment } from "./environments.mjs";
|
|
5
5
|
export { PaidOpenAI } from "./tracing/wrappers/openAiWrapper.mjs";
|
|
6
|
-
export {
|
|
6
|
+
export { PaidAnthropic } from "./tracing/wrappers/anthropicWrapper.mjs";
|
|
7
|
+
export { PaidMistral } from "./tracing/wrappers/mistralWrapper.mjs";
|
|
8
|
+
export { PaidLangChainCallback } from "./tracing/wrappers/langchainCallback.mjs";
|
package/dist/esm/index.mjs
CHANGED
|
@@ -3,4 +3,6 @@ export { PaidClient } from "./Client.mjs";
|
|
|
3
3
|
export { PaidError, PaidTimeoutError } from "./errors/index.mjs";
|
|
4
4
|
export { PaidEnvironment } from "./environments.mjs";
|
|
5
5
|
export { PaidOpenAI } from "./tracing/wrappers/openAiWrapper.mjs";
|
|
6
|
-
export {
|
|
6
|
+
export { PaidAnthropic } from "./tracing/wrappers/anthropicWrapper.mjs";
|
|
7
|
+
export { PaidMistral } from "./tracing/wrappers/mistralWrapper.mjs";
|
|
8
|
+
export { PaidLangChainCallback } from "./tracing/wrappers/langchainCallback.mjs";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function _signal(eventName: string, data?: Record<string, any>): void;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { SpanStatusCode } from "@opentelemetry/api";
|
|
2
|
+
import { getCustomerIdStorage, getAgentIdStorage, getTokenStorage } from "./tracing.mjs";
|
|
3
|
+
import { paidTracer } from "./tracing.mjs";
|
|
4
|
+
export function _signal(eventName, data) {
|
|
5
|
+
if (!eventName) {
|
|
6
|
+
throw new Error("Event name is required for signal.");
|
|
7
|
+
}
|
|
8
|
+
const externalCustomerId = getCustomerIdStorage();
|
|
9
|
+
const externalAgentId = getAgentIdStorage();
|
|
10
|
+
const token = getTokenStorage();
|
|
11
|
+
if (!externalCustomerId || !externalAgentId || !token) {
|
|
12
|
+
throw new Error(`Missing some of: external_customer_id: ${externalCustomerId}, external_agent_id: ${externalAgentId}, or token. Make sure to call signal() within trace()`);
|
|
13
|
+
}
|
|
14
|
+
const tracer = paidTracer;
|
|
15
|
+
tracer.startActiveSpan("trace.signal", (span) => {
|
|
16
|
+
try {
|
|
17
|
+
const attributes = {
|
|
18
|
+
external_customer_id: externalCustomerId,
|
|
19
|
+
external_agent_id: externalAgentId,
|
|
20
|
+
event_name: eventName,
|
|
21
|
+
token: token,
|
|
22
|
+
};
|
|
23
|
+
// Optional data (ex. manual cost tracking)
|
|
24
|
+
if (data) {
|
|
25
|
+
attributes["data"] = JSON.stringify(data);
|
|
26
|
+
}
|
|
27
|
+
span.setAttributes(attributes);
|
|
28
|
+
// Mark span as successful
|
|
29
|
+
span.setStatus({ code: SpanStatusCode.OK });
|
|
30
|
+
}
|
|
31
|
+
catch (error) {
|
|
32
|
+
span.setStatus({
|
|
33
|
+
code: SpanStatusCode.ERROR,
|
|
34
|
+
message: error.message,
|
|
35
|
+
});
|
|
36
|
+
span.recordException(error);
|
|
37
|
+
}
|
|
38
|
+
finally {
|
|
39
|
+
span.end();
|
|
40
|
+
}
|
|
41
|
+
});
|
|
42
|
+
}
|
|
@@ -1,4 +1,8 @@
|
|
|
1
|
-
|
|
1
|
+
import winston from "winston";
|
|
2
|
+
export declare const logger: winston.Logger;
|
|
3
|
+
export declare let paidTracer: import("@opentelemetry/api").Tracer;
|
|
4
|
+
export declare const getCustomerIdStorage: () => string | null | undefined;
|
|
5
|
+
export declare const getAgentIdStorage: () => string | null | undefined;
|
|
2
6
|
export declare const getTokenStorage: () => string | null | undefined;
|
|
3
|
-
export declare function
|
|
4
|
-
export declare function
|
|
7
|
+
export declare function _initializeTracing(apiKey: string, collectorEndpoint?: string): void;
|
|
8
|
+
export declare function _trace<T extends (...args: any[]) => any>(externalCustomerId: string, fn: T, externalAgentId: string | undefined, ...args: Parameters<T>): Promise<ReturnType<T>>;
|
|
@@ -7,50 +7,93 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
7
7
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
8
|
});
|
|
9
9
|
};
|
|
10
|
-
import {
|
|
11
|
-
import { OTLPTraceExporter } from
|
|
12
|
-
import {
|
|
13
|
-
import {
|
|
10
|
+
import { NodeTracerProvider } from "@opentelemetry/sdk-trace-node";
|
|
11
|
+
import { OTLPTraceExporter } from "@opentelemetry/exporter-trace-otlp-http";
|
|
12
|
+
import { BatchSpanProcessor } from "@opentelemetry/sdk-trace-base";
|
|
13
|
+
import { SpanStatusCode } from "@opentelemetry/api";
|
|
14
|
+
import { AsyncLocalStorage } from "async_hooks";
|
|
15
|
+
import winston from "winston";
|
|
16
|
+
export const logger = winston.createLogger({
|
|
17
|
+
level: "silent", // Default to 'silent' to avoid logging unless set via environment variable
|
|
18
|
+
format: winston.format.simple(),
|
|
19
|
+
transports: [new winston.transports.Console()],
|
|
20
|
+
});
|
|
21
|
+
const logLevel = process.env.PAID_LOG_LEVEL;
|
|
22
|
+
if (logLevel) {
|
|
23
|
+
logger.level = logLevel;
|
|
24
|
+
}
|
|
25
|
+
const COLLECTOR_ENDPOINT = process.env.PAID_COLLECTOR_ENDPOINT || "https://collector.agentpaid.io:4318/v1/traces";
|
|
26
|
+
// set up default tracing provider
|
|
27
|
+
let paidExporter = new OTLPTraceExporter({ url: COLLECTOR_ENDPOINT });
|
|
28
|
+
let spanProcessor = new BatchSpanProcessor(paidExporter);
|
|
29
|
+
let paidTracerProvider = new NodeTracerProvider({ spanProcessors: [spanProcessor] });
|
|
30
|
+
export let paidTracer = paidTracerProvider.getTracer("paid.node");
|
|
31
|
+
// storage for passing info to child spans
|
|
14
32
|
const customerIdStorage = new AsyncLocalStorage();
|
|
33
|
+
const agentIdStorage = new AsyncLocalStorage();
|
|
15
34
|
const tokenStorage = new AsyncLocalStorage();
|
|
16
|
-
export const
|
|
35
|
+
export const getCustomerIdStorage = () => customerIdStorage.getStore();
|
|
36
|
+
export const getAgentIdStorage = () => agentIdStorage.getStore();
|
|
17
37
|
export const getTokenStorage = () => tokenStorage.getStore();
|
|
18
38
|
let _token;
|
|
19
|
-
const setToken = (token) => {
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
});
|
|
29
|
-
sdk.start();
|
|
30
|
-
// Graceful shutdown
|
|
31
|
-
['SIGINT', 'SIGTERM'].forEach(signal => {
|
|
39
|
+
const setToken = (token) => {
|
|
40
|
+
_token = token;
|
|
41
|
+
};
|
|
42
|
+
const getToken = () => {
|
|
43
|
+
return _token;
|
|
44
|
+
};
|
|
45
|
+
let _isShuttingDown = false;
|
|
46
|
+
function setupGracefulShutdown(shuttable) {
|
|
47
|
+
["SIGINT", "SIGTERM", "beforeExit", "uncaughtException", "unhandledRejection"].forEach((signal) => {
|
|
32
48
|
process.on(signal, () => {
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
49
|
+
if (_isShuttingDown) {
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
_isShuttingDown = true;
|
|
53
|
+
shuttable
|
|
54
|
+
.shutdown()
|
|
55
|
+
.then(() => logger.info(`Paid tracing SDK shut down from signal: ${signal}`))
|
|
56
|
+
.catch((error) => logger.error(`Error shutting down Paid tracing SDK ${error}`));
|
|
36
57
|
});
|
|
37
58
|
});
|
|
38
59
|
}
|
|
39
|
-
export function
|
|
60
|
+
export function _initializeTracing(apiKey, collectorEndpoint) {
|
|
61
|
+
if (getToken()) {
|
|
62
|
+
throw new Error("Tracing SDK is already initialized.");
|
|
63
|
+
}
|
|
64
|
+
if (!apiKey) {
|
|
65
|
+
throw new Error("Cannot initialize tracing SDK - first initialize the PaidClient with an API key");
|
|
66
|
+
}
|
|
67
|
+
if (collectorEndpoint) {
|
|
68
|
+
paidExporter = new OTLPTraceExporter({ url: collectorEndpoint });
|
|
69
|
+
spanProcessor = new BatchSpanProcessor(paidExporter);
|
|
70
|
+
paidTracerProvider = new NodeTracerProvider({ spanProcessors: [spanProcessor] });
|
|
71
|
+
paidTracer = paidTracerProvider.getTracer("paid.node");
|
|
72
|
+
}
|
|
73
|
+
setupGracefulShutdown(spanProcessor);
|
|
74
|
+
setToken(apiKey);
|
|
75
|
+
const collectorAddress = collectorEndpoint || COLLECTOR_ENDPOINT;
|
|
76
|
+
logger.info(`Paid tracing SDK initialized with collector endpoint: ${collectorAddress}`);
|
|
77
|
+
}
|
|
78
|
+
export function _trace(externalCustomerId, fn, externalAgentId, ...args) {
|
|
40
79
|
return __awaiter(this, void 0, void 0, function* () {
|
|
41
|
-
const tracer =
|
|
80
|
+
const tracer = paidTracer;
|
|
42
81
|
const token = getToken();
|
|
43
|
-
if (!token) {
|
|
44
|
-
|
|
45
|
-
return fn(...args);
|
|
82
|
+
if (!token || !externalCustomerId) {
|
|
83
|
+
throw new Error(`Paid tracing is not initialized. Make sure to call initializeTracing() first.`);
|
|
46
84
|
}
|
|
47
85
|
return tracer.startActiveSpan("paid.node", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
48
|
-
span.setAttribute(
|
|
49
|
-
span.setAttribute(
|
|
86
|
+
span.setAttribute("external_customer_id", externalCustomerId);
|
|
87
|
+
span.setAttribute("token", token);
|
|
88
|
+
if (externalAgentId) {
|
|
89
|
+
span.setAttribute("external_agent_id", externalAgentId);
|
|
90
|
+
}
|
|
50
91
|
try {
|
|
51
92
|
const result = yield customerIdStorage.run(externalCustomerId, () => __awaiter(this, void 0, void 0, function* () {
|
|
52
|
-
return yield
|
|
53
|
-
return yield
|
|
93
|
+
return yield agentIdStorage.run(externalAgentId !== null && externalAgentId !== void 0 ? externalAgentId : null, () => __awaiter(this, void 0, void 0, function* () {
|
|
94
|
+
return yield tokenStorage.run(token, () => __awaiter(this, void 0, void 0, function* () {
|
|
95
|
+
return yield fn(...args);
|
|
96
|
+
}));
|
|
54
97
|
}));
|
|
55
98
|
}));
|
|
56
99
|
span.setStatus({ code: SpanStatusCode.OK });
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import Anthropic from "@anthropic-ai/sdk";
|
|
2
|
+
import { Tracer } from "@opentelemetry/api";
|
|
3
|
+
import { MessageCreateParams } from "@anthropic-ai/sdk/resources/messages";
|
|
4
|
+
export declare class PaidAnthropic {
|
|
5
|
+
private readonly anthropic;
|
|
6
|
+
private readonly tracer;
|
|
7
|
+
constructor(anthropicClient: Anthropic);
|
|
8
|
+
get messages(): MessagesWrapper;
|
|
9
|
+
}
|
|
10
|
+
declare class MessagesWrapper {
|
|
11
|
+
private anthropic;
|
|
12
|
+
private tracer;
|
|
13
|
+
constructor(anthropic: Anthropic, tracer: Tracer);
|
|
14
|
+
create(params: MessageCreateParams): Promise<any>;
|
|
15
|
+
}
|
|
16
|
+
export {};
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
import { SpanStatusCode } from "@opentelemetry/api";
|
|
11
|
+
import { getCustomerIdStorage, getAgentIdStorage, getTokenStorage, paidTracer } from "../tracing.mjs";
|
|
12
|
+
export class PaidAnthropic {
|
|
13
|
+
constructor(anthropicClient) {
|
|
14
|
+
this.anthropic = anthropicClient;
|
|
15
|
+
this.tracer = paidTracer;
|
|
16
|
+
}
|
|
17
|
+
get messages() {
|
|
18
|
+
return new MessagesWrapper(this.anthropic, this.tracer);
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
class MessagesWrapper {
|
|
22
|
+
constructor(anthropic, tracer) {
|
|
23
|
+
this.anthropic = anthropic;
|
|
24
|
+
this.tracer = tracer;
|
|
25
|
+
}
|
|
26
|
+
create(params) {
|
|
27
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
28
|
+
const externalCustomerId = getCustomerIdStorage();
|
|
29
|
+
const externalAgentId = getAgentIdStorage();
|
|
30
|
+
const token = getTokenStorage();
|
|
31
|
+
if (!token || !externalCustomerId) {
|
|
32
|
+
throw new Error("No token or externalCustomerId: This wrapper should be used inside a callback to paid.trace().");
|
|
33
|
+
}
|
|
34
|
+
return this.tracer.startActiveSpan("trace.anthropic.messages", (span) => __awaiter(this, void 0, void 0, function* () {
|
|
35
|
+
const attributes = {
|
|
36
|
+
"gen_ai.system": "anthropic",
|
|
37
|
+
"gen_ai.operation.name": "messages",
|
|
38
|
+
external_customer_id: externalCustomerId,
|
|
39
|
+
token: token,
|
|
40
|
+
};
|
|
41
|
+
if (externalAgentId) {
|
|
42
|
+
attributes["external_agent_id"] = externalAgentId;
|
|
43
|
+
}
|
|
44
|
+
// Set request model from params
|
|
45
|
+
if (params.model) {
|
|
46
|
+
attributes["gen_ai.request.model"] = params.model;
|
|
47
|
+
}
|
|
48
|
+
span.setAttributes(attributes);
|
|
49
|
+
try {
|
|
50
|
+
const response = (yield this.anthropic.messages.create(params));
|
|
51
|
+
// Add usage information from response
|
|
52
|
+
if (response.usage) {
|
|
53
|
+
span.setAttributes({
|
|
54
|
+
"gen_ai.usage.input_tokens": response.usage.input_tokens,
|
|
55
|
+
"gen_ai.usage.output_tokens": response.usage.output_tokens,
|
|
56
|
+
"gen_ai.response.model": response.model,
|
|
57
|
+
});
|
|
58
|
+
// Add Anthropic-specific cache usage if available
|
|
59
|
+
if ("cache_creation_input_tokens" in response.usage && response.usage.cache_creation_input_tokens) {
|
|
60
|
+
span.setAttribute("gen_ai.usage.cache_creation_input_tokens", response.usage.cache_creation_input_tokens);
|
|
61
|
+
}
|
|
62
|
+
if ("cache_read_input_tokens" in response.usage && response.usage.cache_read_input_tokens) {
|
|
63
|
+
span.setAttribute("gen_ai.usage.cache_read_input_tokens", response.usage.cache_read_input_tokens);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
span.setStatus({ code: SpanStatusCode.OK });
|
|
67
|
+
return response;
|
|
68
|
+
}
|
|
69
|
+
catch (error) {
|
|
70
|
+
span.setStatus({ code: SpanStatusCode.ERROR, message: error.message });
|
|
71
|
+
span.recordException(error);
|
|
72
|
+
throw error;
|
|
73
|
+
}
|
|
74
|
+
finally {
|
|
75
|
+
span.end();
|
|
76
|
+
}
|
|
77
|
+
}));
|
|
78
|
+
});
|
|
79
|
+
}
|
|
80
|
+
}
|