@revenium/perplexity 1.0.5 ā 1.0.7
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 +100 -4
- package/dist/perplexity-ai/middleware.js +37 -5
- package/dist/perplexity-ai/middleware.js.map +1 -1
- package/examples/metadata-example.ts +8 -3
- package/package.json +1 -1
- package/playground/basic.js +31 -0
- package/playground/custom-config.js +82 -0
- package/playground/enhanced.js +36 -0
- package/playground/metadata.js +94 -0
- package/playground/multiple-models.js +62 -0
- package/playground/openai-client.js +73 -0
- package/playground/streaming.js +40 -0
- package/src/perplexity-ai/middleware.ts +43 -5
- package/playground/basic-client-example.js +0 -22
package/README.md
CHANGED
|
@@ -31,9 +31,15 @@ import { createPerplexityClient } from "@revenium/perplexity";
|
|
|
31
31
|
config();
|
|
32
32
|
|
|
33
33
|
async function example() {
|
|
34
|
-
// Create client instance
|
|
34
|
+
// Create client instance (uses environment variables by default)
|
|
35
35
|
const client = createPerplexityClient();
|
|
36
36
|
|
|
37
|
+
// Or create with custom API key and base URL
|
|
38
|
+
const customClient = createPerplexityClient(
|
|
39
|
+
"your-api-key",
|
|
40
|
+
"https://api.perplexity.ai"
|
|
41
|
+
);
|
|
42
|
+
|
|
37
43
|
// Make a chat completion
|
|
38
44
|
const response = await client.createChatCompletion({
|
|
39
45
|
model: "sonar-pro",
|
|
@@ -97,8 +103,11 @@ REVENIUM_METERING_BASE_URL=https://api.revenium.io/meter/v2
|
|
|
97
103
|
# Optional: Perplexity base URL (defaults to https://api.perplexity.ai)
|
|
98
104
|
PERPLEXITY_BASE_URL=https://api.perplexity.ai
|
|
99
105
|
|
|
100
|
-
# Optional: Enable verbose logging
|
|
106
|
+
# Optional: Enable verbose logging for debugging
|
|
101
107
|
REVENIUM_VERBOSE_STARTUP=true
|
|
108
|
+
|
|
109
|
+
# Optional: Set log level (DEBUG, INFO, WARNING, ERROR)
|
|
110
|
+
REVENIUM_LOG_LEVEL=INFO
|
|
102
111
|
```
|
|
103
112
|
|
|
104
113
|
## š Examples
|
|
@@ -152,14 +161,22 @@ const stream = await client.createStreamingChatCompletion({
|
|
|
152
161
|
content: "Write a creative story about AI",
|
|
153
162
|
},
|
|
154
163
|
],
|
|
164
|
+
// Optional: Include usage metadata for tracking
|
|
165
|
+
usageMetadata: {
|
|
166
|
+
traceId: "story-generation-001",
|
|
167
|
+
taskType: "creative-writing",
|
|
168
|
+
subscriberEmail: "user@example.com",
|
|
169
|
+
},
|
|
155
170
|
});
|
|
156
171
|
|
|
172
|
+
console.log("š Streaming response:");
|
|
157
173
|
for await (const chunk of stream) {
|
|
158
174
|
const content = chunk.choices[0]?.delta?.content;
|
|
159
175
|
if (content) {
|
|
160
176
|
process.stdout.write(content);
|
|
161
177
|
}
|
|
162
178
|
}
|
|
179
|
+
console.log("\nā
Streaming completed!");
|
|
163
180
|
```
|
|
164
181
|
|
|
165
182
|
## š Usage Metadata
|
|
@@ -247,14 +264,33 @@ npm run run-all-examples
|
|
|
247
264
|
|
|
248
265
|
### PerplexityClient
|
|
249
266
|
|
|
250
|
-
#### `createPerplexityClient(apiKey?: string)`
|
|
267
|
+
#### `createPerplexityClient(apiKey?: string, baseUrl?: string)`
|
|
251
268
|
|
|
252
269
|
Creates a new Perplexity client instance.
|
|
253
270
|
|
|
271
|
+
**Parameters:**
|
|
272
|
+
|
|
273
|
+
- `apiKey` (optional): Your Perplexity API key. If not provided, uses `PERPLEXITY_API_KEY` environment variable.
|
|
274
|
+
- `baseUrl` (optional): Custom base URL for Perplexity API. If not provided, uses `PERPLEXITY_BASE_URL` environment variable or defaults to `https://api.perplexity.ai`.
|
|
275
|
+
|
|
254
276
|
```typescript
|
|
277
|
+
// Using environment variables
|
|
255
278
|
const client = createPerplexityClient();
|
|
256
|
-
|
|
279
|
+
|
|
280
|
+
// With custom API key
|
|
257
281
|
const client = createPerplexityClient("your-api-key");
|
|
282
|
+
|
|
283
|
+
// With custom API key and base URL
|
|
284
|
+
const client = createPerplexityClient(
|
|
285
|
+
"your-api-key",
|
|
286
|
+
"https://api.perplexity.ai"
|
|
287
|
+
);
|
|
288
|
+
|
|
289
|
+
// With custom base URL only (uses env var for API key)
|
|
290
|
+
const client = createPerplexityClient(
|
|
291
|
+
undefined,
|
|
292
|
+
"https://custom-perplexity-endpoint.com"
|
|
293
|
+
);
|
|
258
294
|
```
|
|
259
295
|
|
|
260
296
|
#### `client.createChatCompletion(params)`
|
|
@@ -310,16 +346,74 @@ interface UsageMetadata {
|
|
|
310
346
|
}
|
|
311
347
|
```
|
|
312
348
|
|
|
349
|
+
## š§ Configuration Options
|
|
350
|
+
|
|
351
|
+
### Client Configuration
|
|
352
|
+
|
|
353
|
+
The `createPerplexityClient` function accepts two optional parameters:
|
|
354
|
+
|
|
355
|
+
```typescript
|
|
356
|
+
// All default configuration (uses environment variables)
|
|
357
|
+
const client = createPerplexityClient();
|
|
358
|
+
|
|
359
|
+
// Custom API key only
|
|
360
|
+
const client = createPerplexityClient("your-custom-api-key");
|
|
361
|
+
|
|
362
|
+
// Custom API key and base URL
|
|
363
|
+
const client = createPerplexityClient(
|
|
364
|
+
"your-custom-api-key",
|
|
365
|
+
"https://custom-perplexity-endpoint.com"
|
|
366
|
+
);
|
|
367
|
+
|
|
368
|
+
// Custom base URL only (API key from environment)
|
|
369
|
+
const client = createPerplexityClient(
|
|
370
|
+
undefined,
|
|
371
|
+
"https://custom-perplexity-endpoint.com"
|
|
372
|
+
);
|
|
373
|
+
```
|
|
374
|
+
|
|
375
|
+
### Environment Variable Priority
|
|
376
|
+
|
|
377
|
+
The client follows this priority order for configuration:
|
|
378
|
+
|
|
379
|
+
1. **API Key**: Function parameter ā `PERPLEXITY_API_KEY` environment variable
|
|
380
|
+
2. **Base URL**: Function parameter ā `PERPLEXITY_BASE_URL` environment variable ā Default (`https://api.perplexity.ai`)
|
|
381
|
+
|
|
313
382
|
## š§ Integration Tips
|
|
314
383
|
|
|
315
384
|
### Express.js
|
|
316
385
|
|
|
317
386
|
Load environment variables first, create a separate Perplexity module, and use the patched instance everywhere.
|
|
318
387
|
|
|
388
|
+
```typescript
|
|
389
|
+
// perplexity.js
|
|
390
|
+
import { config } from "dotenv";
|
|
391
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
392
|
+
|
|
393
|
+
config();
|
|
394
|
+
export const perplexityClient = createPerplexityClient();
|
|
395
|
+
```
|
|
396
|
+
|
|
319
397
|
### Next.js
|
|
320
398
|
|
|
321
399
|
Use global variables to prevent re-initialization, works with both Pages and App Router.
|
|
322
400
|
|
|
401
|
+
```typescript
|
|
402
|
+
// lib/perplexity.ts
|
|
403
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
404
|
+
|
|
405
|
+
declare global {
|
|
406
|
+
var perplexityClient: ReturnType<typeof createPerplexityClient> | undefined;
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
export const perplexityClient =
|
|
410
|
+
globalThis.perplexityClient ?? createPerplexityClient();
|
|
411
|
+
|
|
412
|
+
if (process.env.NODE_ENV !== "production") {
|
|
413
|
+
globalThis.perplexityClient = perplexityClient;
|
|
414
|
+
}
|
|
415
|
+
```
|
|
416
|
+
|
|
323
417
|
### Serverless
|
|
324
418
|
|
|
325
419
|
Implement singleton pattern for cold starts, handle CORS for browser clients.
|
|
@@ -335,6 +429,8 @@ Validate environment variables at startup, add health checks for orchestration.
|
|
|
335
429
|
1. **Middleware not activating**: Ensure you're importing the package before creating client instances
|
|
336
430
|
2. **Environment variables**: Verify all required environment variables are set
|
|
337
431
|
3. **API keys**: Check that both Perplexity and Revenium API keys are valid
|
|
432
|
+
4. **Custom base URL**: If using a custom base URL, ensure it's accessible and compatible with Perplexity API
|
|
433
|
+
5. **Module imports**: Make sure you're using the correct import: `import { createPerplexityClient } from "@revenium/perplexity"`
|
|
338
434
|
|
|
339
435
|
### Debug Mode
|
|
340
436
|
|
|
@@ -97,11 +97,43 @@ async function processPerplexityResponse(response, transactionId, model, startTi
|
|
|
97
97
|
try {
|
|
98
98
|
const endTime = new Date();
|
|
99
99
|
const duration = (0, utils_1.calculateDurationMs)(startTime, endTime);
|
|
100
|
-
//
|
|
101
|
-
const
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
100
|
+
// Check if this is a streaming response
|
|
101
|
+
const contentType = response.headers.get("content-type") || "";
|
|
102
|
+
const isStreamingResponse = contentType.includes("text/plain") ||
|
|
103
|
+
contentType.includes("text/event-stream");
|
|
104
|
+
let responseData;
|
|
105
|
+
let tokenCounts = { inputTokens: 0, outputTokens: 0, totalTokens: 0 };
|
|
106
|
+
let stopReason = "END";
|
|
107
|
+
if (isStreamingResponse) {
|
|
108
|
+
// For streaming responses, we can't easily parse the full response
|
|
109
|
+
// We'll extract what we can from the stream or use defaults
|
|
110
|
+
const responseText = await response.text();
|
|
111
|
+
// Try to extract token information from the last complete JSON chunk
|
|
112
|
+
const jsonChunks = responseText
|
|
113
|
+
.split("\n")
|
|
114
|
+
.filter((line) => line.startsWith("data: ") && line !== "data: [DONE]")
|
|
115
|
+
.map((line) => line.substring(6)); // Remove 'data: ' prefix
|
|
116
|
+
if (jsonChunks.length > 0) {
|
|
117
|
+
try {
|
|
118
|
+
// Parse the last chunk to get usage information
|
|
119
|
+
const lastChunk = JSON.parse(jsonChunks[jsonChunks.length - 1]);
|
|
120
|
+
if (lastChunk.usage) {
|
|
121
|
+
tokenCounts = (0, utils_1.extractPerplexityTokenCounts)(lastChunk);
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
catch (e) {
|
|
125
|
+
// If we can't parse, use defaults
|
|
126
|
+
models_1.Logger.warning("Could not parse streaming response for token counts, using defaults");
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
responseData = { usage: tokenCounts };
|
|
130
|
+
}
|
|
131
|
+
else {
|
|
132
|
+
// Parse response body for non-streaming responses
|
|
133
|
+
responseData = await response.json();
|
|
134
|
+
tokenCounts = (0, utils_1.extractPerplexityTokenCounts)(responseData);
|
|
135
|
+
stopReason = (0, utils_1.extractStopReason)(responseData);
|
|
136
|
+
}
|
|
105
137
|
const modelName = (0, utils_1.extractModelName)(responseData, model);
|
|
106
138
|
// Send metering data (only if API key is available)
|
|
107
139
|
if ((0, getEnv_1.getReveniumApiKey)()) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"middleware.js","sourceRoot":"","sources":["../../src/perplexity-ai/middleware.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"middleware.js","sourceRoot":"","sources":["../../src/perplexity-ai/middleware.ts"],"names":[],"mappings":"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"}
|
|
@@ -30,7 +30,10 @@ async function metadataExample() {
|
|
|
30
30
|
},
|
|
31
31
|
});
|
|
32
32
|
|
|
33
|
-
console.log(
|
|
33
|
+
console.log(
|
|
34
|
+
"ā
Response:",
|
|
35
|
+
basicResponse.choices[0]?.message?.content?.substring(0, 100) + "..."
|
|
36
|
+
);
|
|
34
37
|
|
|
35
38
|
// Example 2: Advanced metadata
|
|
36
39
|
console.log("\n2ļøā£ Advanced metadata tracking:");
|
|
@@ -53,7 +56,10 @@ async function metadataExample() {
|
|
|
53
56
|
},
|
|
54
57
|
});
|
|
55
58
|
|
|
56
|
-
console.log(
|
|
59
|
+
console.log(
|
|
60
|
+
"ā
Response:",
|
|
61
|
+
advancedResponse.choices[0]?.message?.content?.substring(0, 100) + "..."
|
|
62
|
+
);
|
|
57
63
|
|
|
58
64
|
// Example 3: Streaming with metadata
|
|
59
65
|
console.log("\n3ļøā£ Streaming with metadata:");
|
|
@@ -83,7 +89,6 @@ async function metadataExample() {
|
|
|
83
89
|
|
|
84
90
|
console.log("\n\nš All metadata examples completed successfully!");
|
|
85
91
|
console.log("š All usage tracked with custom metadata");
|
|
86
|
-
|
|
87
92
|
} catch (error) {
|
|
88
93
|
console.error("ā Error:", error);
|
|
89
94
|
}
|
package/package.json
CHANGED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
const basicExample = async () => {
|
|
4
|
+
console.log("\nš¤ Perplexity AI - Basic Client Example");
|
|
5
|
+
console.log("=".repeat(50));
|
|
6
|
+
|
|
7
|
+
try {
|
|
8
|
+
// Create client instance
|
|
9
|
+
const client = createPerplexityClient();
|
|
10
|
+
|
|
11
|
+
// Make a simple chat completion
|
|
12
|
+
const response = await client.createChatCompletion({
|
|
13
|
+
model: "sonar-pro",
|
|
14
|
+
messages: [
|
|
15
|
+
{
|
|
16
|
+
role: "user",
|
|
17
|
+
content: "What is the meaning of life, the universe and everything?",
|
|
18
|
+
},
|
|
19
|
+
],
|
|
20
|
+
});
|
|
21
|
+
|
|
22
|
+
console.log("ā
Response received:");
|
|
23
|
+
console.log(response.choices[0].message.content);
|
|
24
|
+
console.log("\nš Token usage automatically tracked by middleware");
|
|
25
|
+
console.log("š Basic client example successful!");
|
|
26
|
+
} catch (error) {
|
|
27
|
+
console.error("ā Error:", error);
|
|
28
|
+
}
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
basicExample();
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
async function customConfigExample() {
|
|
4
|
+
console.log("\nāļø Perplexity AI - Custom Configuration Example");
|
|
5
|
+
console.log("=".repeat(50));
|
|
6
|
+
|
|
7
|
+
try {
|
|
8
|
+
// Example 1: Using environment variables (default)
|
|
9
|
+
console.log("\n1ļøā£ Using environment variables:");
|
|
10
|
+
const defaultClient = createPerplexityClient();
|
|
11
|
+
|
|
12
|
+
const response1 = await defaultClient.createChatCompletion({
|
|
13
|
+
model: "sonar-pro",
|
|
14
|
+
messages: [
|
|
15
|
+
{
|
|
16
|
+
role: "user",
|
|
17
|
+
content: "Hello from default configuration!",
|
|
18
|
+
},
|
|
19
|
+
],
|
|
20
|
+
});
|
|
21
|
+
console.log("ā
Default config response:", response1.choices[0]?.message?.content?.substring(0, 50) + "...");
|
|
22
|
+
|
|
23
|
+
// Example 2: Custom API key only
|
|
24
|
+
console.log("\n2ļøā£ Using custom API key:");
|
|
25
|
+
const customKeyClient = createPerplexityClient(process.env.PERPLEXITY_API_KEY);
|
|
26
|
+
|
|
27
|
+
const response2 = await customKeyClient.createChatCompletion({
|
|
28
|
+
model: "sonar-pro",
|
|
29
|
+
messages: [
|
|
30
|
+
{
|
|
31
|
+
role: "user",
|
|
32
|
+
content: "Hello from custom API key configuration!",
|
|
33
|
+
},
|
|
34
|
+
],
|
|
35
|
+
});
|
|
36
|
+
console.log("ā
Custom key response:", response2.choices[0]?.message?.content?.substring(0, 50) + "...");
|
|
37
|
+
|
|
38
|
+
// Example 3: Custom API key and base URL
|
|
39
|
+
console.log("\n3ļøā£ Using custom API key and base URL:");
|
|
40
|
+
const fullCustomClient = createPerplexityClient(
|
|
41
|
+
process.env.PERPLEXITY_API_KEY,
|
|
42
|
+
"https://api.perplexity.ai"
|
|
43
|
+
);
|
|
44
|
+
|
|
45
|
+
const response3 = await fullCustomClient.createChatCompletion({
|
|
46
|
+
model: "sonar-pro",
|
|
47
|
+
messages: [
|
|
48
|
+
{
|
|
49
|
+
role: "user",
|
|
50
|
+
content: "Hello from fully custom configuration!",
|
|
51
|
+
},
|
|
52
|
+
],
|
|
53
|
+
});
|
|
54
|
+
console.log("ā
Full custom response:", response3.choices[0]?.message?.content?.substring(0, 50) + "...");
|
|
55
|
+
|
|
56
|
+
// Example 4: Custom base URL only (API key from env)
|
|
57
|
+
console.log("\n4ļøā£ Using custom base URL only:");
|
|
58
|
+
const customUrlClient = createPerplexityClient(
|
|
59
|
+
undefined,
|
|
60
|
+
"https://api.perplexity.ai"
|
|
61
|
+
);
|
|
62
|
+
|
|
63
|
+
const response4 = await customUrlClient.createChatCompletion({
|
|
64
|
+
model: "sonar-pro",
|
|
65
|
+
messages: [
|
|
66
|
+
{
|
|
67
|
+
role: "user",
|
|
68
|
+
content: "Hello from custom URL configuration!",
|
|
69
|
+
},
|
|
70
|
+
],
|
|
71
|
+
});
|
|
72
|
+
console.log("ā
Custom URL response:", response4.choices[0]?.message?.content?.substring(0, 50) + "...");
|
|
73
|
+
|
|
74
|
+
console.log("\nš All configuration examples completed successfully!");
|
|
75
|
+
console.log("š All requests tracked by middleware regardless of configuration");
|
|
76
|
+
|
|
77
|
+
} catch (error) {
|
|
78
|
+
console.error("ā Error:", error);
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
customConfigExample();
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
const enhancedExample = async () => {
|
|
4
|
+
console.log("\n1ļøā£ Enhanced Example:");
|
|
5
|
+
|
|
6
|
+
try {
|
|
7
|
+
const client = createPerplexityClient();
|
|
8
|
+
const advancedResponse = await client.createChatCompletion({
|
|
9
|
+
model: "sonar-pro",
|
|
10
|
+
messages: [
|
|
11
|
+
{
|
|
12
|
+
role: "user",
|
|
13
|
+
content: "What are the latest developments in AI?",
|
|
14
|
+
},
|
|
15
|
+
],
|
|
16
|
+
usageMetadata: {
|
|
17
|
+
traceId: "conv-advanced-123",
|
|
18
|
+
taskType: "research",
|
|
19
|
+
subscriberId: "user-12345",
|
|
20
|
+
subscriberCredentialName: "api-key-1",
|
|
21
|
+
productId: "business-intelligence",
|
|
22
|
+
agent: "research-assistant-v2",
|
|
23
|
+
responseQualityScore: 0.95,
|
|
24
|
+
},
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
console.log(
|
|
28
|
+
"ā
Response:",
|
|
29
|
+
advancedResponse.choices[0]?.message?.content?.substring(0, 100) + "..."
|
|
30
|
+
);
|
|
31
|
+
} catch (error) {
|
|
32
|
+
console.error("ā Error:", error);
|
|
33
|
+
}
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
enhancedExample();
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
async function metadataExample() {
|
|
4
|
+
console.log("\nš Perplexity AI - Metadata Tracking Example");
|
|
5
|
+
console.log("=".repeat(50));
|
|
6
|
+
|
|
7
|
+
try {
|
|
8
|
+
// Create client instance
|
|
9
|
+
const client = createPerplexityClient();
|
|
10
|
+
|
|
11
|
+
// Example 1: Basic metadata
|
|
12
|
+
console.log("\n1ļøā£ Basic metadata tracking:");
|
|
13
|
+
const basicResponse = await client.createChatCompletion({
|
|
14
|
+
model: "sonar-pro",
|
|
15
|
+
messages: [
|
|
16
|
+
{
|
|
17
|
+
role: "user",
|
|
18
|
+
content: "Analyze this quarterly report for key insights",
|
|
19
|
+
},
|
|
20
|
+
],
|
|
21
|
+
usageMetadata: {
|
|
22
|
+
traceId: "conv-28a7e9d4",
|
|
23
|
+
taskType: "document-analysis",
|
|
24
|
+
subscriberEmail: "user@example.com",
|
|
25
|
+
organizationId: "acme-corp",
|
|
26
|
+
subscriptionId: "premium-plan",
|
|
27
|
+
},
|
|
28
|
+
});
|
|
29
|
+
|
|
30
|
+
console.log(
|
|
31
|
+
"ā
Response:",
|
|
32
|
+
basicResponse.choices[0]?.message?.content?.substring(0, 100) + "..."
|
|
33
|
+
);
|
|
34
|
+
|
|
35
|
+
// Example 2: Advanced metadata
|
|
36
|
+
console.log("\n2ļøā£ Advanced metadata tracking:");
|
|
37
|
+
const advancedResponse = await client.createChatCompletion({
|
|
38
|
+
model: "sonar-pro",
|
|
39
|
+
messages: [
|
|
40
|
+
{
|
|
41
|
+
role: "user",
|
|
42
|
+
content: "What are the latest developments in AI?",
|
|
43
|
+
},
|
|
44
|
+
],
|
|
45
|
+
usageMetadata: {
|
|
46
|
+
traceId: "conv-advanced-123",
|
|
47
|
+
taskType: "research",
|
|
48
|
+
subscriberId: "user-12345",
|
|
49
|
+
subscriberCredentialName: "api-key-1",
|
|
50
|
+
productId: "business-intelligence",
|
|
51
|
+
agent: "research-assistant-v2",
|
|
52
|
+
responseQualityScore: 0.95,
|
|
53
|
+
},
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
console.log(
|
|
57
|
+
"ā
Response:",
|
|
58
|
+
advancedResponse.choices[0]?.message?.content?.substring(0, 100) + "..."
|
|
59
|
+
);
|
|
60
|
+
|
|
61
|
+
// Example 3: Streaming with metadata
|
|
62
|
+
console.log("\n3ļøā£ Streaming with metadata:");
|
|
63
|
+
const stream = await client.createStreamingChatCompletion({
|
|
64
|
+
model: "sonar-pro",
|
|
65
|
+
messages: [
|
|
66
|
+
{
|
|
67
|
+
role: "user",
|
|
68
|
+
content: "Write a creative story about AI",
|
|
69
|
+
},
|
|
70
|
+
],
|
|
71
|
+
usageMetadata: {
|
|
72
|
+
traceId: "conv-streaming-456",
|
|
73
|
+
taskType: "creative-writing",
|
|
74
|
+
organizationId: "creative-studio",
|
|
75
|
+
agent: "story-generator",
|
|
76
|
+
},
|
|
77
|
+
});
|
|
78
|
+
|
|
79
|
+
console.log("š Streaming response with metadata:");
|
|
80
|
+
for await (const chunk of stream) {
|
|
81
|
+
const content = chunk.choices[0]?.delta?.content;
|
|
82
|
+
if (content) {
|
|
83
|
+
process.stdout.write(content);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
console.log("\n\nš All metadata examples completed successfully!");
|
|
88
|
+
console.log("š All usage tracked with custom metadata");
|
|
89
|
+
} catch (error) {
|
|
90
|
+
console.error("ā Error:", error);
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
metadataExample();
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
async function multipleModelsExample() {
|
|
4
|
+
console.log("\nš§ Perplexity AI - Multiple Models Example");
|
|
5
|
+
console.log("=".repeat(50));
|
|
6
|
+
|
|
7
|
+
try {
|
|
8
|
+
// Create client instance
|
|
9
|
+
const client = createPerplexityClient();
|
|
10
|
+
|
|
11
|
+
// Test different prompts with the same model
|
|
12
|
+
const testCases = [
|
|
13
|
+
{
|
|
14
|
+
name: "sonar-pro (Quantum Computing)",
|
|
15
|
+
description: "Latest and most capable model",
|
|
16
|
+
prompt: "Explain quantum computing in simple terms",
|
|
17
|
+
},
|
|
18
|
+
{
|
|
19
|
+
name: "sonar-pro (AI Developments)",
|
|
20
|
+
description: "Latest and most capable model",
|
|
21
|
+
prompt: "What are the latest developments in AI?",
|
|
22
|
+
},
|
|
23
|
+
{
|
|
24
|
+
name: "sonar-pro (Weather)",
|
|
25
|
+
description: "Latest and most capable model",
|
|
26
|
+
prompt: "What is the weather like today?",
|
|
27
|
+
},
|
|
28
|
+
];
|
|
29
|
+
|
|
30
|
+
for (const testCase of testCases) {
|
|
31
|
+
console.log(`\nš¤ Testing: ${testCase.name}`);
|
|
32
|
+
console.log(`š Description: ${testCase.description}`);
|
|
33
|
+
console.log("-".repeat(40));
|
|
34
|
+
|
|
35
|
+
try {
|
|
36
|
+
const response = await client.createChatCompletion({
|
|
37
|
+
model: "sonar-pro",
|
|
38
|
+
messages: [
|
|
39
|
+
{
|
|
40
|
+
role: "user",
|
|
41
|
+
content: testCase.prompt,
|
|
42
|
+
},
|
|
43
|
+
],
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
console.log("ā
Response:");
|
|
47
|
+
console.log(response.choices[0]?.message?.content?.substring(0, 200) + "...");
|
|
48
|
+
console.log("š Usage tracked by middleware");
|
|
49
|
+
|
|
50
|
+
} catch (error) {
|
|
51
|
+
console.log(`ā Error with ${testCase.name}:`, error);
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
console.log("\nš Multiple models example completed!");
|
|
56
|
+
|
|
57
|
+
} catch (error) {
|
|
58
|
+
console.error("ā Error:", error);
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
multipleModelsExample();
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
import { OpenAI } from "openai";
|
|
2
|
+
|
|
3
|
+
// Import middleware to activate automatic tracking
|
|
4
|
+
import "@revenium/perplexity";
|
|
5
|
+
|
|
6
|
+
async function openaiClientExample() {
|
|
7
|
+
console.log("\nš¤ Perplexity AI - OpenAI Client Example");
|
|
8
|
+
console.log("=".repeat(50));
|
|
9
|
+
|
|
10
|
+
try {
|
|
11
|
+
// Create OpenAI client configured for Perplexity (like in basic example)
|
|
12
|
+
const client = new OpenAI({
|
|
13
|
+
apiKey: process.env.PERPLEXITY_API_KEY,
|
|
14
|
+
baseURL: "https://api.perplexity.ai",
|
|
15
|
+
});
|
|
16
|
+
|
|
17
|
+
console.log("ā
OpenAI client configured for Perplexity AI");
|
|
18
|
+
console.log("š Middleware automatically tracking all requests");
|
|
19
|
+
|
|
20
|
+
// Test different types of requests
|
|
21
|
+
console.log("\n1ļøā£ Basic chat completion:");
|
|
22
|
+
const basicResponse = await client.chat.completions.create({
|
|
23
|
+
model: "sonar-pro",
|
|
24
|
+
messages: [
|
|
25
|
+
{
|
|
26
|
+
role: "user",
|
|
27
|
+
content: "What is the meaning of life, the universe and everything?",
|
|
28
|
+
},
|
|
29
|
+
],
|
|
30
|
+
});
|
|
31
|
+
console.log("ā
Response:", basicResponse.choices[0]?.message?.content?.substring(0, 100) + "...");
|
|
32
|
+
|
|
33
|
+
console.log("\n2ļøā£ Streaming chat completion:");
|
|
34
|
+
const stream = await client.chat.completions.create({
|
|
35
|
+
model: "sonar-pro",
|
|
36
|
+
messages: [
|
|
37
|
+
{
|
|
38
|
+
role: "user",
|
|
39
|
+
content: "Write a short poem about AI",
|
|
40
|
+
},
|
|
41
|
+
],
|
|
42
|
+
stream: true,
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
console.log("š Streaming response:");
|
|
46
|
+
for await (const chunk of stream) {
|
|
47
|
+
const content = chunk.choices[0]?.delta?.content;
|
|
48
|
+
if (content) {
|
|
49
|
+
process.stdout.write(content);
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
console.log("\n\n3ļøā£ Different prompt:");
|
|
54
|
+
const differentResponse = await client.chat.completions.create({
|
|
55
|
+
model: "sonar-pro",
|
|
56
|
+
messages: [
|
|
57
|
+
{
|
|
58
|
+
role: "user",
|
|
59
|
+
content: "Explain machine learning in one sentence",
|
|
60
|
+
},
|
|
61
|
+
],
|
|
62
|
+
});
|
|
63
|
+
console.log("ā
Response:", differentResponse.choices[0]?.message?.content);
|
|
64
|
+
|
|
65
|
+
console.log("\nš All examples completed successfully!");
|
|
66
|
+
console.log("š All usage automatically tracked by middleware");
|
|
67
|
+
|
|
68
|
+
} catch (error) {
|
|
69
|
+
console.error("ā Error:", error);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
openaiClientExample();
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
+
|
|
3
|
+
async function streamingExample() {
|
|
4
|
+
console.log("\nš Perplexity AI - Streaming Example");
|
|
5
|
+
console.log("=".repeat(50));
|
|
6
|
+
|
|
7
|
+
try {
|
|
8
|
+
const client = createPerplexityClient();
|
|
9
|
+
console.log("\n3ļøā£ Streaming with metadata:");
|
|
10
|
+
const stream = await client.createStreamingChatCompletion({
|
|
11
|
+
model: "sonar-pro",
|
|
12
|
+
messages: [
|
|
13
|
+
{
|
|
14
|
+
role: "user",
|
|
15
|
+
content: "Write a creative story about AI",
|
|
16
|
+
},
|
|
17
|
+
],
|
|
18
|
+
usageMetadata: {
|
|
19
|
+
traceId: "conv-streaming-456",
|
|
20
|
+
taskType: "creative-writing",
|
|
21
|
+
organizationId: "creative-studio",
|
|
22
|
+
agent: "story-generator",
|
|
23
|
+
},
|
|
24
|
+
});
|
|
25
|
+
|
|
26
|
+
console.log("š Streaming response with metadata:");
|
|
27
|
+
for await (const chunk of stream) {
|
|
28
|
+
const content = chunk.choices[0]?.delta?.content;
|
|
29
|
+
if (content) {
|
|
30
|
+
process.stdout.write(content);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
console.log("\n\nš Streaming completed!");
|
|
35
|
+
} catch (error) {
|
|
36
|
+
console.error("ā Error:", error);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
streamingExample();
|
|
@@ -186,12 +186,50 @@ async function processPerplexityResponse(
|
|
|
186
186
|
const endTime = new Date();
|
|
187
187
|
const duration = calculateDurationMs(startTime, endTime);
|
|
188
188
|
|
|
189
|
-
//
|
|
190
|
-
const
|
|
189
|
+
// Check if this is a streaming response
|
|
190
|
+
const contentType = response.headers.get("content-type") || "";
|
|
191
|
+
const isStreamingResponse =
|
|
192
|
+
contentType.includes("text/plain") ||
|
|
193
|
+
contentType.includes("text/event-stream");
|
|
194
|
+
|
|
195
|
+
let responseData: any;
|
|
196
|
+
let tokenCounts = { inputTokens: 0, outputTokens: 0, totalTokens: 0 };
|
|
197
|
+
let stopReason = "END";
|
|
198
|
+
|
|
199
|
+
if (isStreamingResponse) {
|
|
200
|
+
// For streaming responses, we can't easily parse the full response
|
|
201
|
+
// We'll extract what we can from the stream or use defaults
|
|
202
|
+
const responseText = await response.text();
|
|
203
|
+
|
|
204
|
+
// Try to extract token information from the last complete JSON chunk
|
|
205
|
+
const jsonChunks = responseText
|
|
206
|
+
.split("\n")
|
|
207
|
+
.filter((line) => line.startsWith("data: ") && line !== "data: [DONE]")
|
|
208
|
+
.map((line) => line.substring(6)); // Remove 'data: ' prefix
|
|
209
|
+
|
|
210
|
+
if (jsonChunks.length > 0) {
|
|
211
|
+
try {
|
|
212
|
+
// Parse the last chunk to get usage information
|
|
213
|
+
const lastChunk = JSON.parse(jsonChunks[jsonChunks.length - 1]);
|
|
214
|
+
if (lastChunk.usage) {
|
|
215
|
+
tokenCounts = extractPerplexityTokenCounts(lastChunk);
|
|
216
|
+
}
|
|
217
|
+
} catch (e) {
|
|
218
|
+
// If we can't parse, use defaults
|
|
219
|
+
Logger.warning(
|
|
220
|
+
"Could not parse streaming response for token counts, using defaults"
|
|
221
|
+
);
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
responseData = { usage: tokenCounts };
|
|
226
|
+
} else {
|
|
227
|
+
// Parse response body for non-streaming responses
|
|
228
|
+
responseData = await response.json();
|
|
229
|
+
tokenCounts = extractPerplexityTokenCounts(responseData);
|
|
230
|
+
stopReason = extractStopReason(responseData);
|
|
231
|
+
}
|
|
191
232
|
|
|
192
|
-
// Extract token counts and other data
|
|
193
|
-
const tokenCounts = extractPerplexityTokenCounts(responseData);
|
|
194
|
-
const stopReason = extractStopReason(responseData);
|
|
195
233
|
const modelName = extractModelName(responseData, model);
|
|
196
234
|
|
|
197
235
|
// Send metering data (only if API key is available)
|
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
import { createPerplexityClient } from "@revenium/perplexity";
|
|
2
|
-
|
|
3
|
-
async function basicExample() {
|
|
4
|
-
const client = createPerplexityClient();
|
|
5
|
-
|
|
6
|
-
const response = await client.createChatCompletion({
|
|
7
|
-
model: "sonar-pro",
|
|
8
|
-
messages: [
|
|
9
|
-
{
|
|
10
|
-
role: "user",
|
|
11
|
-
content: "What is the meaning of life, the universe and everything?",
|
|
12
|
-
},
|
|
13
|
-
],
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
console.log("ā
Response received:");
|
|
17
|
-
console.log(response.choices[0].message.content);
|
|
18
|
-
console.log("\nš Token usage automatically tracked by middleware");
|
|
19
|
-
console.log("š Basic client example successful!");
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
basicExample();
|