@agentstats/sdk 0.5.0 → 0.5.1
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 +10 -0
- package/dist/bots.cjs +1022 -0
- package/dist/bots.d.cts +265 -0
- package/dist/bots.d.ts +265 -0
- package/dist/bots.js +1010 -0
- package/dist/browser.iife.js +1 -1
- package/dist/index.cjs +3 -6
- package/dist/index.d.cts +1 -5
- package/dist/index.d.ts +1 -5
- package/dist/index.js +3 -6
- package/dist/lite.iife.js +1 -1
- package/dist/server.cjs +293 -204
- package/dist/server.d.cts +76 -18
- package/dist/server.d.ts +76 -18
- package/dist/server.js +293 -204
- package/package.json +21 -12
package/dist/server.d.cts
CHANGED
|
@@ -1,12 +1,35 @@
|
|
|
1
|
-
//#region src/bots.d.ts
|
|
2
1
|
/**
|
|
3
|
-
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
2
|
+
* AgentStats server integration — see which AI crawlers and agents visit your
|
|
3
|
+
* site (GPTBot, ClaudeBot, PerplexityBot, ChatGPT agent, Google-Agent, …),
|
|
4
|
+
* including the ones that never run JavaScript.
|
|
6
5
|
*
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
6
|
+
* Runs on Node and on edge runtimes (no Node built-ins). What leaves your server:
|
|
7
|
+
* - bot-like requests: method, URL, status, user agent, IP (used to verify the
|
|
8
|
+
* bot against the vendor's published ranges, then discarded) and Web Bot Auth
|
|
9
|
+
* signature headers;
|
|
10
|
+
* - visits referred by an AI assistant (chatgpt.com, perplexity.ai, …): URL and
|
|
11
|
+
* referrer host only;
|
|
12
|
+
* - everything else: a per-day count of page views. Nothing about humans.
|
|
13
|
+
*
|
|
14
|
+
* import { createAgentStats } from '@agentstats/sdk/server'
|
|
15
|
+
* const lens = createAgentStats({ serverKey: process.env.AGENTSTATS_SERVER_KEY })
|
|
16
|
+
* app.use(lens.express()) // Express / Connect: res.locals.bot
|
|
17
|
+
* export default defineNitroPlugin(lens.nitro()) // Nuxt / Nitro: event.context.bot
|
|
18
|
+
* export const handle = lens.sveltekit() // SvelteKit: event.locals.bot
|
|
19
|
+
* export const onRequest = lens.astro() // Astro: Astro.locals.bot
|
|
20
|
+
* app.use(lens.hono()) // Hono: c.get('bot')
|
|
21
|
+
* lens.track(request, { waitUntil, response }) // Next.js proxy, Workers, Bun, Deno
|
|
22
|
+
*
|
|
23
|
+
* Every adapter also hands you `detectBot()`'s answer for the request, and `detectBot`
|
|
24
|
+
* works on its own (no key needed): `detectBot(request).isAI`.
|
|
25
|
+
*
|
|
26
|
+
* With an `apiKey` (an API's key, `al_api_…`), the same adapters also track your API: calls an
|
|
27
|
+
* AI agent made (a Web Bot Auth signature, an `X-AI-Agent` header, an agent's User-Agent, or a
|
|
28
|
+
* credential you name in `apiCaller`) with method, route pattern, status and duration, and a
|
|
29
|
+
* per-day count of every other call. Never bodies, query strings or credentials: the caller is
|
|
30
|
+
* sent as an HMAC of its credential, keyed with your API key.
|
|
31
|
+
*
|
|
32
|
+
* const lens = createAgentStats({ apiKey: process.env.AGENTSTATS_API_KEY }) // API-only server
|
|
10
33
|
*/
|
|
11
34
|
type BotCategory = 'training' | 'search' | 'assistant' | 'agent' | 'search_engine' | 'other';
|
|
12
35
|
/** Categories that count as "AI traffic". Search engines and other bots are shown separately. */
|
|
@@ -126,6 +149,10 @@ export declare const BOT_PRODUCTS: {
|
|
|
126
149
|
name: string;
|
|
127
150
|
operator: string;
|
|
128
151
|
};
|
|
152
|
+
ai: {
|
|
153
|
+
name: string;
|
|
154
|
+
operator: string;
|
|
155
|
+
};
|
|
129
156
|
coding: {
|
|
130
157
|
name: string;
|
|
131
158
|
operator: string;
|
|
@@ -138,6 +165,10 @@ export declare const BOT_PRODUCTS: {
|
|
|
138
165
|
name: string;
|
|
139
166
|
operator: string;
|
|
140
167
|
};
|
|
168
|
+
searchengines: {
|
|
169
|
+
name: string;
|
|
170
|
+
operator: string;
|
|
171
|
+
};
|
|
141
172
|
automation: {
|
|
142
173
|
name: string;
|
|
143
174
|
operator: string;
|
|
@@ -154,6 +185,26 @@ export declare const BOT_PRODUCTS: {
|
|
|
154
185
|
name: string;
|
|
155
186
|
operator: string;
|
|
156
187
|
};
|
|
188
|
+
feeds: {
|
|
189
|
+
name: string;
|
|
190
|
+
operator: string;
|
|
191
|
+
};
|
|
192
|
+
security: {
|
|
193
|
+
name: string;
|
|
194
|
+
operator: string;
|
|
195
|
+
};
|
|
196
|
+
archive: {
|
|
197
|
+
name: string;
|
|
198
|
+
operator: string;
|
|
199
|
+
};
|
|
200
|
+
research: {
|
|
201
|
+
name: string;
|
|
202
|
+
operator: string;
|
|
203
|
+
};
|
|
204
|
+
ads: {
|
|
205
|
+
name: string;
|
|
206
|
+
operator: string;
|
|
207
|
+
};
|
|
157
208
|
tools: {
|
|
158
209
|
name: string;
|
|
159
210
|
operator: string;
|
|
@@ -171,11 +222,10 @@ interface BotPattern {
|
|
|
171
222
|
category: BotCategory;
|
|
172
223
|
/** Matched against the User-Agent header. `null` = only identified another way (signature). */
|
|
173
224
|
pattern: RegExp | null;
|
|
225
|
+
/** Who runs it, when its product groups several vendors ("Other AI bots"). Else the product's operator. */
|
|
226
|
+
operator?: string;
|
|
174
227
|
}
|
|
175
|
-
/**
|
|
176
|
-
* Order matters: the first matching pattern wins, so specific tokens come
|
|
177
|
-
* before the vendor's generic ones and the catch-all patterns come last.
|
|
178
|
-
*/
|
|
228
|
+
/** Every bot this SDK recognises, in the order they're tried: the first match wins, catch-alls last. */
|
|
179
229
|
export declare const BOT_PATTERNS: BotPattern[];
|
|
180
230
|
/** Identify a bot from its User-Agent. Returns null for (what looks like) a normal browser. */
|
|
181
231
|
export declare function classifyUserAgent(ua: string | null | undefined): BotPattern | null;
|
|
@@ -226,16 +276,14 @@ type DetectInput = Request | Headers | {
|
|
|
226
276
|
* detectBot(req) // Node / Express IncomingMessage
|
|
227
277
|
*/
|
|
228
278
|
export declare function detectBot(input: DetectInput): BotDetection;
|
|
229
|
-
|
|
230
|
-
//#region src/server.d.ts
|
|
231
|
-
export declare const SERVER_SDK_VERSION = "0.3.1";
|
|
279
|
+
export declare const SERVER_SDK_VERSION = "0.3.2";
|
|
232
280
|
export interface ServerOptions {
|
|
233
281
|
/**
|
|
234
282
|
* Secret server key from Site settings (`al_srv_…`). Never expose it to browsers.
|
|
235
283
|
* Without one, the adapters still detect bots but nothing is sent.
|
|
236
284
|
*/
|
|
237
285
|
serverKey?: string | undefined;
|
|
238
|
-
/** Hits endpoint
|
|
286
|
+
/** Hits endpoint. Defaults to `AGENTSTATS_ENDPOINT`, then `https://agentstats.io/api/ingest/hits`. */
|
|
239
287
|
endpoint?: string;
|
|
240
288
|
/**
|
|
241
289
|
* Secret key of an API in your project (Project settings → APIs, `al_api_…`). Turns on API
|
|
@@ -380,6 +428,7 @@ export declare class AgentStatsServer {
|
|
|
380
428
|
track(request: Request, init?: {
|
|
381
429
|
status?: number | null;
|
|
382
430
|
ip?: string | null;
|
|
431
|
+
remoteAddress?: string | null;
|
|
383
432
|
response?: {
|
|
384
433
|
headers: Headers;
|
|
385
434
|
} | null;
|
|
@@ -411,9 +460,10 @@ export declare class AgentStatsServer {
|
|
|
411
460
|
/** Astro: `export const onRequest = lens.astro()` in `src/middleware.ts` (or inside `sequence()`). The detection is on `Astro.locals.bot`. */
|
|
412
461
|
astro(): (context: AstroContextLike, next: () => Promise<Response>) => Promise<Response>;
|
|
413
462
|
/**
|
|
414
|
-
* Nuxt / Nitro plugin: `export default defineNitroPlugin(lens.nitro())` in `server/plugins/agentstats.ts
|
|
463
|
+
* Nuxt / Nitro plugin: `export default defineNitroPlugin(lens.nitro())` in `server/plugins/agentstats.ts`
|
|
464
|
+
* (Nitro v3: `export default definePlugin(lens.nitro())`).
|
|
415
465
|
* The detection is on `event.context.bot` in server routes, and on `useRequestEvent()?.context.bot` in pages.
|
|
416
|
-
* Works on every Nitro preset (Node, Vercel, Netlify, Cloudflare…).
|
|
466
|
+
* Works on every Nitro preset (Node, Vercel, Netlify, Cloudflare…), on Nitro v2 (h3 v1) and v3 (h3 v2).
|
|
417
467
|
*/
|
|
418
468
|
nitro(): (nitroApp: {
|
|
419
469
|
hooks: {
|
|
@@ -509,8 +559,16 @@ export interface H3EventLike {
|
|
|
509
559
|
web?: {
|
|
510
560
|
request?: Request;
|
|
511
561
|
};
|
|
562
|
+
/** h3 v2 (Nitro v3): the request (srvx adds `ip`), its parsed URL and the response being prepared. */
|
|
563
|
+
req?: Request & {
|
|
564
|
+
ip?: string;
|
|
565
|
+
};
|
|
566
|
+
url?: URL;
|
|
567
|
+
res?: {
|
|
568
|
+
status?: number;
|
|
569
|
+
headers: Headers;
|
|
570
|
+
};
|
|
512
571
|
waitUntil?: WaitUntil;
|
|
513
572
|
}
|
|
514
573
|
export declare function createAgentStats(options: ServerOptions): AgentStatsServer;
|
|
515
|
-
//#endregion
|
|
516
574
|
export { type BotCategory, type BotDetection, type BotPattern, type BotProduct, type BotProductId, type DetectInput, createAgentStats as default };
|
package/dist/server.d.ts
CHANGED
|
@@ -1,12 +1,35 @@
|
|
|
1
|
-
//#region src/bots.d.ts
|
|
2
1
|
/**
|
|
3
|
-
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
2
|
+
* AgentStats server integration — see which AI crawlers and agents visit your
|
|
3
|
+
* site (GPTBot, ClaudeBot, PerplexityBot, ChatGPT agent, Google-Agent, …),
|
|
4
|
+
* including the ones that never run JavaScript.
|
|
6
5
|
*
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
6
|
+
* Runs on Node and on edge runtimes (no Node built-ins). What leaves your server:
|
|
7
|
+
* - bot-like requests: method, URL, status, user agent, IP (used to verify the
|
|
8
|
+
* bot against the vendor's published ranges, then discarded) and Web Bot Auth
|
|
9
|
+
* signature headers;
|
|
10
|
+
* - visits referred by an AI assistant (chatgpt.com, perplexity.ai, …): URL and
|
|
11
|
+
* referrer host only;
|
|
12
|
+
* - everything else: a per-day count of page views. Nothing about humans.
|
|
13
|
+
*
|
|
14
|
+
* import { createAgentStats } from '@agentstats/sdk/server'
|
|
15
|
+
* const lens = createAgentStats({ serverKey: process.env.AGENTSTATS_SERVER_KEY })
|
|
16
|
+
* app.use(lens.express()) // Express / Connect: res.locals.bot
|
|
17
|
+
* export default defineNitroPlugin(lens.nitro()) // Nuxt / Nitro: event.context.bot
|
|
18
|
+
* export const handle = lens.sveltekit() // SvelteKit: event.locals.bot
|
|
19
|
+
* export const onRequest = lens.astro() // Astro: Astro.locals.bot
|
|
20
|
+
* app.use(lens.hono()) // Hono: c.get('bot')
|
|
21
|
+
* lens.track(request, { waitUntil, response }) // Next.js proxy, Workers, Bun, Deno
|
|
22
|
+
*
|
|
23
|
+
* Every adapter also hands you `detectBot()`'s answer for the request, and `detectBot`
|
|
24
|
+
* works on its own (no key needed): `detectBot(request).isAI`.
|
|
25
|
+
*
|
|
26
|
+
* With an `apiKey` (an API's key, `al_api_…`), the same adapters also track your API: calls an
|
|
27
|
+
* AI agent made (a Web Bot Auth signature, an `X-AI-Agent` header, an agent's User-Agent, or a
|
|
28
|
+
* credential you name in `apiCaller`) with method, route pattern, status and duration, and a
|
|
29
|
+
* per-day count of every other call. Never bodies, query strings or credentials: the caller is
|
|
30
|
+
* sent as an HMAC of its credential, keyed with your API key.
|
|
31
|
+
*
|
|
32
|
+
* const lens = createAgentStats({ apiKey: process.env.AGENTSTATS_API_KEY }) // API-only server
|
|
10
33
|
*/
|
|
11
34
|
type BotCategory = 'training' | 'search' | 'assistant' | 'agent' | 'search_engine' | 'other';
|
|
12
35
|
/** Categories that count as "AI traffic". Search engines and other bots are shown separately. */
|
|
@@ -126,6 +149,10 @@ export declare const BOT_PRODUCTS: {
|
|
|
126
149
|
name: string;
|
|
127
150
|
operator: string;
|
|
128
151
|
};
|
|
152
|
+
ai: {
|
|
153
|
+
name: string;
|
|
154
|
+
operator: string;
|
|
155
|
+
};
|
|
129
156
|
coding: {
|
|
130
157
|
name: string;
|
|
131
158
|
operator: string;
|
|
@@ -138,6 +165,10 @@ export declare const BOT_PRODUCTS: {
|
|
|
138
165
|
name: string;
|
|
139
166
|
operator: string;
|
|
140
167
|
};
|
|
168
|
+
searchengines: {
|
|
169
|
+
name: string;
|
|
170
|
+
operator: string;
|
|
171
|
+
};
|
|
141
172
|
automation: {
|
|
142
173
|
name: string;
|
|
143
174
|
operator: string;
|
|
@@ -154,6 +185,26 @@ export declare const BOT_PRODUCTS: {
|
|
|
154
185
|
name: string;
|
|
155
186
|
operator: string;
|
|
156
187
|
};
|
|
188
|
+
feeds: {
|
|
189
|
+
name: string;
|
|
190
|
+
operator: string;
|
|
191
|
+
};
|
|
192
|
+
security: {
|
|
193
|
+
name: string;
|
|
194
|
+
operator: string;
|
|
195
|
+
};
|
|
196
|
+
archive: {
|
|
197
|
+
name: string;
|
|
198
|
+
operator: string;
|
|
199
|
+
};
|
|
200
|
+
research: {
|
|
201
|
+
name: string;
|
|
202
|
+
operator: string;
|
|
203
|
+
};
|
|
204
|
+
ads: {
|
|
205
|
+
name: string;
|
|
206
|
+
operator: string;
|
|
207
|
+
};
|
|
157
208
|
tools: {
|
|
158
209
|
name: string;
|
|
159
210
|
operator: string;
|
|
@@ -171,11 +222,10 @@ interface BotPattern {
|
|
|
171
222
|
category: BotCategory;
|
|
172
223
|
/** Matched against the User-Agent header. `null` = only identified another way (signature). */
|
|
173
224
|
pattern: RegExp | null;
|
|
225
|
+
/** Who runs it, when its product groups several vendors ("Other AI bots"). Else the product's operator. */
|
|
226
|
+
operator?: string;
|
|
174
227
|
}
|
|
175
|
-
/**
|
|
176
|
-
* Order matters: the first matching pattern wins, so specific tokens come
|
|
177
|
-
* before the vendor's generic ones and the catch-all patterns come last.
|
|
178
|
-
*/
|
|
228
|
+
/** Every bot this SDK recognises, in the order they're tried: the first match wins, catch-alls last. */
|
|
179
229
|
export declare const BOT_PATTERNS: BotPattern[];
|
|
180
230
|
/** Identify a bot from its User-Agent. Returns null for (what looks like) a normal browser. */
|
|
181
231
|
export declare function classifyUserAgent(ua: string | null | undefined): BotPattern | null;
|
|
@@ -226,16 +276,14 @@ type DetectInput = Request | Headers | {
|
|
|
226
276
|
* detectBot(req) // Node / Express IncomingMessage
|
|
227
277
|
*/
|
|
228
278
|
export declare function detectBot(input: DetectInput): BotDetection;
|
|
229
|
-
|
|
230
|
-
//#region src/server.d.ts
|
|
231
|
-
export declare const SERVER_SDK_VERSION = "0.3.1";
|
|
279
|
+
export declare const SERVER_SDK_VERSION = "0.3.2";
|
|
232
280
|
export interface ServerOptions {
|
|
233
281
|
/**
|
|
234
282
|
* Secret server key from Site settings (`al_srv_…`). Never expose it to browsers.
|
|
235
283
|
* Without one, the adapters still detect bots but nothing is sent.
|
|
236
284
|
*/
|
|
237
285
|
serverKey?: string | undefined;
|
|
238
|
-
/** Hits endpoint
|
|
286
|
+
/** Hits endpoint. Defaults to `AGENTSTATS_ENDPOINT`, then `https://agentstats.io/api/ingest/hits`. */
|
|
239
287
|
endpoint?: string;
|
|
240
288
|
/**
|
|
241
289
|
* Secret key of an API in your project (Project settings → APIs, `al_api_…`). Turns on API
|
|
@@ -380,6 +428,7 @@ export declare class AgentStatsServer {
|
|
|
380
428
|
track(request: Request, init?: {
|
|
381
429
|
status?: number | null;
|
|
382
430
|
ip?: string | null;
|
|
431
|
+
remoteAddress?: string | null;
|
|
383
432
|
response?: {
|
|
384
433
|
headers: Headers;
|
|
385
434
|
} | null;
|
|
@@ -411,9 +460,10 @@ export declare class AgentStatsServer {
|
|
|
411
460
|
/** Astro: `export const onRequest = lens.astro()` in `src/middleware.ts` (or inside `sequence()`). The detection is on `Astro.locals.bot`. */
|
|
412
461
|
astro(): (context: AstroContextLike, next: () => Promise<Response>) => Promise<Response>;
|
|
413
462
|
/**
|
|
414
|
-
* Nuxt / Nitro plugin: `export default defineNitroPlugin(lens.nitro())` in `server/plugins/agentstats.ts
|
|
463
|
+
* Nuxt / Nitro plugin: `export default defineNitroPlugin(lens.nitro())` in `server/plugins/agentstats.ts`
|
|
464
|
+
* (Nitro v3: `export default definePlugin(lens.nitro())`).
|
|
415
465
|
* The detection is on `event.context.bot` in server routes, and on `useRequestEvent()?.context.bot` in pages.
|
|
416
|
-
* Works on every Nitro preset (Node, Vercel, Netlify, Cloudflare…).
|
|
466
|
+
* Works on every Nitro preset (Node, Vercel, Netlify, Cloudflare…), on Nitro v2 (h3 v1) and v3 (h3 v2).
|
|
417
467
|
*/
|
|
418
468
|
nitro(): (nitroApp: {
|
|
419
469
|
hooks: {
|
|
@@ -509,8 +559,16 @@ export interface H3EventLike {
|
|
|
509
559
|
web?: {
|
|
510
560
|
request?: Request;
|
|
511
561
|
};
|
|
562
|
+
/** h3 v2 (Nitro v3): the request (srvx adds `ip`), its parsed URL and the response being prepared. */
|
|
563
|
+
req?: Request & {
|
|
564
|
+
ip?: string;
|
|
565
|
+
};
|
|
566
|
+
url?: URL;
|
|
567
|
+
res?: {
|
|
568
|
+
status?: number;
|
|
569
|
+
headers: Headers;
|
|
570
|
+
};
|
|
512
571
|
waitUntil?: WaitUntil;
|
|
513
572
|
}
|
|
514
573
|
export declare function createAgentStats(options: ServerOptions): AgentStatsServer;
|
|
515
|
-
//#endregion
|
|
516
574
|
export { type BotCategory, type BotDetection, type BotPattern, type BotProduct, type BotProductId, type DetectInput, createAgentStats as default };
|