tokoscope 0.1.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/index.js +58 -0
- package/package.json +26 -0
package/index.js
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
const ENDPOINT = 'https://us-central1-tokoscope-e8ab2.cloudfunctions.net/trackEvent'
|
|
2
|
+
|
|
3
|
+
function wrap(client, { apiKey }) {
|
|
4
|
+
if (!apiKey) throw new Error('Tokoscope: apiKey is required')
|
|
5
|
+
|
|
6
|
+
async function track({ provider, model, inputTokens, outputTokens, prompt, endpoint }) {
|
|
7
|
+
try {
|
|
8
|
+
await fetch(ENDPOINT, {
|
|
9
|
+
method: 'POST',
|
|
10
|
+
headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${apiKey}` },
|
|
11
|
+
body: JSON.stringify({ provider, model, inputTokens, outputTokens, prompt, endpoint })
|
|
12
|
+
})
|
|
13
|
+
} catch (e) {
|
|
14
|
+
// Silent fail — never break the main app
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
// Detect provider type
|
|
19
|
+
const isAnthropic = typeof client.messages?.create === 'function' && !client.chat
|
|
20
|
+
|
|
21
|
+
if (isAnthropic) {
|
|
22
|
+
// Wrap Anthropic
|
|
23
|
+
const originalCreate = client.messages.create.bind(client.messages)
|
|
24
|
+
client.messages.create = async function(params) {
|
|
25
|
+
const result = await originalCreate(params)
|
|
26
|
+
const prompt = params.messages?.map(m => typeof m.content === 'string' ? m.content : '').join(' ')
|
|
27
|
+
await track({
|
|
28
|
+
provider: 'anthropic',
|
|
29
|
+
model: params.model,
|
|
30
|
+
inputTokens: result.usage?.input_tokens || 0,
|
|
31
|
+
outputTokens: result.usage?.output_tokens || 0,
|
|
32
|
+
prompt,
|
|
33
|
+
endpoint: params.model
|
|
34
|
+
})
|
|
35
|
+
return result
|
|
36
|
+
}
|
|
37
|
+
} else {
|
|
38
|
+
// Wrap OpenAI
|
|
39
|
+
const originalCreate = client.chat.completions.create.bind(client.chat.completions)
|
|
40
|
+
client.chat.completions.create = async function(params) {
|
|
41
|
+
const result = await originalCreate(params)
|
|
42
|
+
const prompt = params.messages?.map(m => m.content || '').join(' ')
|
|
43
|
+
await track({
|
|
44
|
+
provider: 'openai',
|
|
45
|
+
model: params.model,
|
|
46
|
+
inputTokens: result.usage?.prompt_tokens || 0,
|
|
47
|
+
outputTokens: result.usage?.completion_tokens || 0,
|
|
48
|
+
prompt,
|
|
49
|
+
endpoint: params.model
|
|
50
|
+
})
|
|
51
|
+
return result
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
return client
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
module.exports = { wrap }
|
package/package.json
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "tokoscope",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Audit, compress and monitor your LLM token usage in 2 lines of code",
|
|
5
|
+
"main": "index.js",
|
|
6
|
+
"type": "commonjs",
|
|
7
|
+
"scripts": {
|
|
8
|
+
"test": "echo \"No tests yet\""
|
|
9
|
+
},
|
|
10
|
+
"keywords": [
|
|
11
|
+
"llm",
|
|
12
|
+
"openai",
|
|
13
|
+
"anthropic",
|
|
14
|
+
"tokens",
|
|
15
|
+
"optimization",
|
|
16
|
+
"cost",
|
|
17
|
+
"monitoring"
|
|
18
|
+
],
|
|
19
|
+
"author": "Tokoscope",
|
|
20
|
+
"license": "MIT",
|
|
21
|
+
"homepage": "https://tokoscope.com",
|
|
22
|
+
"repository": {
|
|
23
|
+
"type": "git",
|
|
24
|
+
"url": "https://github.com/tokoscope/tokoscope-sdk"
|
|
25
|
+
}
|
|
26
|
+
}
|