@diegoaltoworks/chatter 0.50.0 โ 0.52.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/README.md +18 -1
- package/dist/channels/gates.d.ts +17 -1
- package/dist/channels/gates.d.ts.map +1 -1
- package/dist/channels/index.d.ts +1 -1
- package/dist/channels/index.d.ts.map +1 -1
- package/dist/channels/index.js +17 -4
- package/dist/channels/index.mjs +17 -4
- package/dist/channels/whatsapp/index.js +17 -4
- package/dist/channels/whatsapp/index.mjs +17 -4
- package/dist/index.js +3 -3
- package/dist/index.mjs +3 -3
- package/dist/middleware/clientKey.d.ts +5 -5
- package/dist/middleware/securityHeaders.d.ts +3 -1
- package/dist/middleware/securityHeaders.d.ts.map +1 -1
- package/dist/server.js +3 -3
- package/dist/server.mjs +3 -3
- package/dist/types.d.ts +4 -2
- package/dist/types.d.ts.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -26,6 +26,12 @@
|
|
|
26
26
|
- โก **High Performance**: Built on Hono with streaming support
|
|
27
27
|
- ๐ก๏ธ **Security First**: Rate limiting, CORS, referrer checking, and input guardrails
|
|
28
28
|
- ๐ธ **Usage Metering**: Per-caller and global daily caps for paid features, multi-instance safe, via `@diegoaltoworks/chatter/usage` ([guide](./docs/usage.md))
|
|
29
|
+
- ๐ฌ **Channels**: Built-in WhatsApp transport plus a Channel SPI for plugging in any other one โ allowlist/mute gates, reply rate-limiting, and a shared inbound pipeline every channel reuses ([WhatsApp guide](./docs/channels.md), [build your own](./docs/build-a-channel.md))
|
|
30
|
+
- ๐งฉ **Flows**: Multi-turn, schema-driven slot-filling for structured conversations, with hybrid keyword + LLM intent matching ([guide](./docs/flows.md))
|
|
31
|
+
- ๐ผ๏ธ **Images**: On-demand generation and editing with cache-before-spend ordering and optional Cloudinary upload ([guide](./docs/images.md))
|
|
32
|
+
- ๐ญ **Personas**: Windowed, per-contact prompt layers and named greetings from a JSON registry ([guide](./docs/personas.md))
|
|
33
|
+
- ๐๏ธ **Conversation History**: Structural, multi-turn context store, multi-instance safe and host-replaceable ([guide](./docs/history.md))
|
|
34
|
+
- โฐ **Scheduler**: Exactly-once outbound scheduling with a fire-time grace window, multi-instance safe ([guide](./docs/scheduler.md))
|
|
29
35
|
- ๐ฆ **Framework Agnostic**: Works with any JavaScript framework or vanilla JS
|
|
30
36
|
- ๐ฏ **TypeScript**: Fully typed for excellent developer experience
|
|
31
37
|
|
|
@@ -84,13 +90,24 @@ is runtime-neutral. Development and the quality gates run on Bun.
|
|
|
84
90
|
|
|
85
91
|
## Documentation
|
|
86
92
|
|
|
87
|
-
Complete guides for setup, deployment, and integration
|
|
93
|
+
Complete guides for setup, deployment, and integration โ see
|
|
94
|
+
[docs/index.md](./docs/index.md) for the full, ordered walkthrough:
|
|
88
95
|
|
|
96
|
+
- **[Architecture](./docs/ARCHITECTURE.md)** - Load-bearing invariants, each linked to the test that enforces it
|
|
89
97
|
- **[Requirements](./docs/requirements.md)** - OpenAI, Turso, Clerk setup and pricing
|
|
90
98
|
- **[Server Setup](./docs/server.md)** - Configuration, knowledge base, prompts, API keys
|
|
91
99
|
- **[Client Integration](./docs/client.md)** - Widgets, React components, theming
|
|
100
|
+
- **[UI Integrations](./docs/integrations.md)** - OpenAI-compatible API, headless mode, bring-your-own-brain
|
|
92
101
|
- **[Usage Metering](./docs/usage.md)** - Daily spend caps for paid features
|
|
102
|
+
- **[Personas](./docs/personas.md)** - Dynamic prompt layers and named greetings
|
|
103
|
+
- **[WhatsApp Channel](./docs/channels.md)** - Link a WhatsApp number as a transport
|
|
104
|
+
- **[Building a Channel](./docs/build-a-channel.md)** - Plug in a new transport
|
|
105
|
+
- **[Flows](./docs/flows.md)** - Multi-turn, schema-driven slot-filling flows
|
|
106
|
+
- **[Images](./docs/images.md)** - Generate and cache images on demand
|
|
107
|
+
- **[Conversation History](./docs/history.md)** - Structural, host-replaceable multi-turn context
|
|
108
|
+
- **[Scheduler](./docs/scheduler.md)** - Exactly-once outbound scheduling
|
|
93
109
|
- **[Deployment](./docs/deployment.md)** - Google Cloud Run, Fly.io, Railway, VPS
|
|
110
|
+
- **[Packaging](./docs/packaging.md)** - The subpath contract and the release chain
|
|
94
111
|
- **[Testing](./docs/testing.md)** - Comprehensive testing guide
|
|
95
112
|
- **[Sprint Review](./docs/sprint-review.md)** - Cross-module & security-invariant audit
|
|
96
113
|
- **[FAQs](./docs/faqs.md)** - Troubleshooting and common questions
|
package/dist/channels/gates.d.ts
CHANGED
|
@@ -59,8 +59,24 @@ export declare function decideChannelAction(msg: ChannelMessage, config: Channel
|
|
|
59
59
|
* Sliding-window rate limiter (pure, injectable clock): true = allowed and
|
|
60
60
|
* counted. One instance guards one budget โ callers wanting separate DM and
|
|
61
61
|
* group budgets create two (see {@link underReplyRateLimit}).
|
|
62
|
+
*
|
|
63
|
+
* Keyed by chatId, which โ unlike an IP โ a caller can't rotate at will, but
|
|
64
|
+
* a long-lived deployment still accumulates one entry per chat it has ever
|
|
65
|
+
* seen, including chats that never come back. A global sweep (same shape as
|
|
66
|
+
* `windowBucket.ts`'s) runs at most once per window, on a call for any key,
|
|
67
|
+
* and drops every key whose entries have all fallen out of the window โ
|
|
68
|
+
* bounding the map to chats active within roughly the last two windows
|
|
69
|
+
* instead of growing for the life of the process. `allow.size()` reports
|
|
70
|
+
* the current key count, for tests asserting eviction actually happened.
|
|
71
|
+
*
|
|
72
|
+
* @internal `size` is an observability hook for this module's own tests, not
|
|
73
|
+
* part of the public contract โ callers should treat the return value as a
|
|
74
|
+
* plain `(key: string) => boolean`.
|
|
62
75
|
*/
|
|
63
|
-
export declare function createSlidingWindowRateLimiter(maxPerWindow: number, windowMs: number, now?: () => number):
|
|
76
|
+
export declare function createSlidingWindowRateLimiter(maxPerWindow: number, windowMs: number, now?: () => number): {
|
|
77
|
+
(key: string): boolean;
|
|
78
|
+
size: () => number;
|
|
79
|
+
};
|
|
64
80
|
/**
|
|
65
81
|
* Routes a chat to its DM or group rate limiter so a flood in one can't
|
|
66
82
|
* spend the other's budget โ a DM flood used to be entirely unthrottled
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"gates.d.ts","sourceRoot":"","sources":["../../src/channels/gates.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,iFAAiF;AACjF,MAAM,WAAW,cAAc;IAC7B,yEAAyE;IACzE,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,iFAAiF;IACjF,eAAe,EAAE,OAAO,CAAC;IACzB,mEAAmE;IACnE,WAAW,EAAE,OAAO,CAAC;IACrB,wFAAwF;IACxF,YAAY,EAAE,OAAO,CAAC;IACtB,sHAAsH;IACtH,OAAO,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,QAAQ,GAAG,MAAM,GAAG,QAAQ,CAAC;AAEnE,MAAM,WAAW,iBAAiB;IAChC,gGAAgG;IAChG,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,kIAAkI;IAClI,UAAU,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;IACxB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAOD;;;;;;;GAOG;AACH,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,cAAc,EACnB,MAAM,EAAE,IAAI,CAAC,iBAAiB,EAAE,cAAc,CAAC,GAC9C,OAAO,CAQT;AAED;;;;;;;GAOG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,cAAc,EAAE,MAAM,EAAE,iBAAiB,GAAG,aAAa,CAUjG;AAED
|
|
1
|
+
{"version":3,"file":"gates.d.ts","sourceRoot":"","sources":["../../src/channels/gates.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,iFAAiF;AACjF,MAAM,WAAW,cAAc;IAC7B,yEAAyE;IACzE,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,iFAAiF;IACjF,eAAe,EAAE,OAAO,CAAC;IACzB,mEAAmE;IACnE,WAAW,EAAE,OAAO,CAAC;IACrB,wFAAwF;IACxF,YAAY,EAAE,OAAO,CAAC;IACtB,sHAAsH;IACtH,OAAO,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,QAAQ,GAAG,MAAM,GAAG,QAAQ,CAAC;AAEnE,MAAM,WAAW,iBAAiB;IAChC,gGAAgG;IAChG,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,kIAAkI;IAClI,UAAU,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;IACxB;;;;OAIG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAOD;;;;;;;GAOG;AACH,wBAAgB,oBAAoB,CAClC,GAAG,EAAE,cAAc,EACnB,MAAM,EAAE,IAAI,CAAC,iBAAiB,EAAE,cAAc,CAAC,GAC9C,OAAO,CAQT;AAED;;;;;;;GAOG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,cAAc,EAAE,MAAM,EAAE,iBAAiB,GAAG,aAAa,CAUjG;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,8BAA8B,CAC5C,YAAY,EAAE,MAAM,EACpB,QAAQ,EAAE,MAAM,EAChB,GAAG,GAAE,MAAM,MAAiB;UAcR,MAAM,GAAG,OAAO;;EAiBrC;AAED;;;;;GAKG;AACH,wBAAgB,mBAAmB,CACjC,GAAG,EAAE,IAAI,CAAC,cAAc,EAAE,QAAQ,GAAG,iBAAiB,CAAC,EACvD,QAAQ,EAAE;IAAE,EAAE,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,OAAO,CAAC;IAAC,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,OAAO,CAAA;CAAE,GAChF,OAAO,CAET;AAED;;;;;;;;;;;;;;GAcG;AACH,MAAM,MAAM,uBAAuB,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;AAE5D,qHAAqH;AACrH,wBAAgB,gBAAgB,CAC9B,EAAE,EAAE,MAAM,GAAG,SAAS,EACtB,QAAQ,EAAE,uBAAuB,GAChC,OAAO,CAMT;AAED;;;;;GAKG;AACH,wBAAgB,qBAAqB,CACnC,GAAG,EAAE,IAAI,CAAC,cAAc,EAAE,SAAS,GAAG,UAAU,CAAC,EACjD,QAAQ,EAAE,uBAAuB,GAChC,OAAO,CAET"}
|
package/dist/channels/index.d.ts
CHANGED
|
@@ -42,7 +42,7 @@ export interface Channel {
|
|
|
42
42
|
stop?(): void | Promise<void>;
|
|
43
43
|
}
|
|
44
44
|
export * from "./gates";
|
|
45
|
-
export { createInboundPipeline, type InboundPipelineConfig, type InboundPipelineDeps, type InboundPipelineOutcome, type InboundReplySender, type InboundTurn, } from "./pipeline";
|
|
45
|
+
export { createInboundPipeline, type InboundPipeline, type InboundPipelineConfig, type InboundPipelineDeps, type InboundPipelineOutcome, type InboundReplySender, type InboundTurn, } from "./pipeline";
|
|
46
46
|
export type { ChannelSender, ChannelSenderRegistry } from "./senders";
|
|
47
47
|
export { createSenderRegistry } from "./senders";
|
|
48
48
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/channels/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,UAAU,CAAC;AAEnD,MAAM,WAAW,OAAO;IACtB,2FAA2F;IAC3F,IAAI,EAAE,MAAM,CAAC;IACb;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,IAAI,EAAE,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACtD;;;;;;OAMG;IACH,IAAI,CAAC,IAAI,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CAC/B;AAED,cAAc,SAAS,CAAC;AACxB,OAAO,EACL,qBAAqB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,mBAAmB,EACxB,KAAK,sBAAsB,EAC3B,KAAK,kBAAkB,EACvB,KAAK,WAAW,GACjB,MAAM,YAAY,CAAC;AACpB,YAAY,EAAE,aAAa,EAAE,qBAAqB,EAAE,MAAM,WAAW,CAAC;AACtE,OAAO,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/channels/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,UAAU,CAAC;AAEnD,MAAM,WAAW,OAAO;IACtB,2FAA2F;IAC3F,IAAI,EAAE,MAAM,CAAC;IACb;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,IAAI,EAAE,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACtD;;;;;;OAMG;IACH,IAAI,CAAC,IAAI,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CAC/B;AAED,cAAc,SAAS,CAAC;AACxB,OAAO,EACL,qBAAqB,EACrB,KAAK,eAAe,EACpB,KAAK,qBAAqB,EAC1B,KAAK,mBAAmB,EACxB,KAAK,sBAAsB,EAC3B,KAAK,kBAAkB,EACvB,KAAK,WAAW,GACjB,MAAM,YAAY,CAAC;AACpB,YAAY,EAAE,aAAa,EAAE,qBAAqB,EAAE,MAAM,WAAW,CAAC;AACtE,OAAO,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC"}
|
package/dist/channels/index.js
CHANGED
|
@@ -51,18 +51,31 @@ function decideChannelAction(msg, config) {
|
|
|
51
51
|
}
|
|
52
52
|
function createSlidingWindowRateLimiter(maxPerWindow, windowMs, now = Date.now) {
|
|
53
53
|
const log = /* @__PURE__ */ new Map();
|
|
54
|
-
|
|
55
|
-
|
|
54
|
+
let lastSweep = now();
|
|
55
|
+
function sweep(current) {
|
|
56
|
+
if (current - lastSweep < windowMs) return;
|
|
57
|
+
lastSweep = current;
|
|
58
|
+
const cutoff = current - windowMs;
|
|
59
|
+
for (const [key, entries] of log) {
|
|
60
|
+
if (!entries.some((t) => t > cutoff)) log.delete(key);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
function allow(key) {
|
|
64
|
+
const current = now();
|
|
65
|
+
sweep(current);
|
|
66
|
+
const cutoff = current - windowMs;
|
|
56
67
|
const entries = (log.get(key) ?? []).filter((t) => t > cutoff);
|
|
57
68
|
if (entries.length >= maxPerWindow) {
|
|
58
69
|
if (entries.length > 0) log.set(key, entries);
|
|
59
70
|
else log.delete(key);
|
|
60
71
|
return false;
|
|
61
72
|
}
|
|
62
|
-
entries.push(
|
|
73
|
+
entries.push(current);
|
|
63
74
|
log.set(key, entries);
|
|
64
75
|
return true;
|
|
65
|
-
}
|
|
76
|
+
}
|
|
77
|
+
allow.size = () => log.size;
|
|
78
|
+
return allow;
|
|
66
79
|
}
|
|
67
80
|
function underReplyRateLimit(msg, limiters) {
|
|
68
81
|
return msg.isDirectMessage ? limiters.dm(msg.chatId) : limiters.group(msg.chatId);
|
package/dist/channels/index.mjs
CHANGED
|
@@ -18,18 +18,31 @@ function decideChannelAction(msg, config) {
|
|
|
18
18
|
}
|
|
19
19
|
function createSlidingWindowRateLimiter(maxPerWindow, windowMs, now = Date.now) {
|
|
20
20
|
const log = /* @__PURE__ */ new Map();
|
|
21
|
-
|
|
22
|
-
|
|
21
|
+
let lastSweep = now();
|
|
22
|
+
function sweep(current) {
|
|
23
|
+
if (current - lastSweep < windowMs) return;
|
|
24
|
+
lastSweep = current;
|
|
25
|
+
const cutoff = current - windowMs;
|
|
26
|
+
for (const [key, entries] of log) {
|
|
27
|
+
if (!entries.some((t) => t > cutoff)) log.delete(key);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
function allow(key) {
|
|
31
|
+
const current = now();
|
|
32
|
+
sweep(current);
|
|
33
|
+
const cutoff = current - windowMs;
|
|
23
34
|
const entries = (log.get(key) ?? []).filter((t) => t > cutoff);
|
|
24
35
|
if (entries.length >= maxPerWindow) {
|
|
25
36
|
if (entries.length > 0) log.set(key, entries);
|
|
26
37
|
else log.delete(key);
|
|
27
38
|
return false;
|
|
28
39
|
}
|
|
29
|
-
entries.push(
|
|
40
|
+
entries.push(current);
|
|
30
41
|
log.set(key, entries);
|
|
31
42
|
return true;
|
|
32
|
-
}
|
|
43
|
+
}
|
|
44
|
+
allow.size = () => log.size;
|
|
45
|
+
return allow;
|
|
33
46
|
}
|
|
34
47
|
function underReplyRateLimit(msg, limiters) {
|
|
35
48
|
return msg.isDirectMessage ? limiters.dm(msg.chatId) : limiters.group(msg.chatId);
|
|
@@ -624,18 +624,31 @@ function decideChannelAction(msg, config) {
|
|
|
624
624
|
}
|
|
625
625
|
function createSlidingWindowRateLimiter(maxPerWindow, windowMs, now = Date.now) {
|
|
626
626
|
const log = /* @__PURE__ */ new Map();
|
|
627
|
-
|
|
628
|
-
|
|
627
|
+
let lastSweep = now();
|
|
628
|
+
function sweep(current) {
|
|
629
|
+
if (current - lastSweep < windowMs) return;
|
|
630
|
+
lastSweep = current;
|
|
631
|
+
const cutoff = current - windowMs;
|
|
632
|
+
for (const [key, entries] of log) {
|
|
633
|
+
if (!entries.some((t) => t > cutoff)) log.delete(key);
|
|
634
|
+
}
|
|
635
|
+
}
|
|
636
|
+
function allow(key) {
|
|
637
|
+
const current = now();
|
|
638
|
+
sweep(current);
|
|
639
|
+
const cutoff = current - windowMs;
|
|
629
640
|
const entries = (log.get(key) ?? []).filter((t) => t > cutoff);
|
|
630
641
|
if (entries.length >= maxPerWindow) {
|
|
631
642
|
if (entries.length > 0) log.set(key, entries);
|
|
632
643
|
else log.delete(key);
|
|
633
644
|
return false;
|
|
634
645
|
}
|
|
635
|
-
entries.push(
|
|
646
|
+
entries.push(current);
|
|
636
647
|
log.set(key, entries);
|
|
637
648
|
return true;
|
|
638
|
-
}
|
|
649
|
+
}
|
|
650
|
+
allow.size = () => log.size;
|
|
651
|
+
return allow;
|
|
639
652
|
}
|
|
640
653
|
function underReplyRateLimit(msg, limiters) {
|
|
641
654
|
return msg.isDirectMessage ? limiters.dm(msg.chatId) : limiters.group(msg.chatId);
|
|
@@ -562,18 +562,31 @@ function decideChannelAction(msg, config) {
|
|
|
562
562
|
}
|
|
563
563
|
function createSlidingWindowRateLimiter(maxPerWindow, windowMs, now = Date.now) {
|
|
564
564
|
const log = /* @__PURE__ */ new Map();
|
|
565
|
-
|
|
566
|
-
|
|
565
|
+
let lastSweep = now();
|
|
566
|
+
function sweep(current) {
|
|
567
|
+
if (current - lastSweep < windowMs) return;
|
|
568
|
+
lastSweep = current;
|
|
569
|
+
const cutoff = current - windowMs;
|
|
570
|
+
for (const [key, entries] of log) {
|
|
571
|
+
if (!entries.some((t) => t > cutoff)) log.delete(key);
|
|
572
|
+
}
|
|
573
|
+
}
|
|
574
|
+
function allow(key) {
|
|
575
|
+
const current = now();
|
|
576
|
+
sweep(current);
|
|
577
|
+
const cutoff = current - windowMs;
|
|
567
578
|
const entries = (log.get(key) ?? []).filter((t) => t > cutoff);
|
|
568
579
|
if (entries.length >= maxPerWindow) {
|
|
569
580
|
if (entries.length > 0) log.set(key, entries);
|
|
570
581
|
else log.delete(key);
|
|
571
582
|
return false;
|
|
572
583
|
}
|
|
573
|
-
entries.push(
|
|
584
|
+
entries.push(current);
|
|
574
585
|
log.set(key, entries);
|
|
575
586
|
return true;
|
|
576
|
-
}
|
|
587
|
+
}
|
|
588
|
+
allow.size = () => log.size;
|
|
589
|
+
return allow;
|
|
577
590
|
}
|
|
578
591
|
function underReplyRateLimit(msg, limiters) {
|
|
579
592
|
return msg.isDirectMessage ? limiters.dm(msg.chatId) : limiters.group(msg.chatId);
|
package/dist/index.js
CHANGED
|
@@ -1294,7 +1294,7 @@ function createRateLimiter2(config) {
|
|
|
1294
1294
|
const limiter = createWindowBucketLimiter(6e4);
|
|
1295
1295
|
const publicLimit = config.rateLimit?.public || 60;
|
|
1296
1296
|
const privateLimit = config.rateLimit?.private || 120;
|
|
1297
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1297
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1298
1298
|
const demoApiKeys = config.rateLimit?.demoApiKeys ?? [];
|
|
1299
1299
|
return {
|
|
1300
1300
|
// Public: key is IP only
|
|
@@ -1396,7 +1396,7 @@ function isHttps(c, trustProxy) {
|
|
|
1396
1396
|
function securityHeaders(config) {
|
|
1397
1397
|
const csp = config.server?.contentSecurityPolicy || DEFAULT_CSP;
|
|
1398
1398
|
const hsts = config.server?.strictTransportSecurity ?? DEFAULT_HSTS;
|
|
1399
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1399
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1400
1400
|
return async (c, next) => {
|
|
1401
1401
|
await next();
|
|
1402
1402
|
c.header("content-security-policy", csp);
|
|
@@ -1498,7 +1498,7 @@ function demoRoutes(deps) {
|
|
|
1498
1498
|
const app = new import_hono.Hono();
|
|
1499
1499
|
const demoOrigins = config.server?.allowedOrigins ?? [];
|
|
1500
1500
|
const allowLocalhostDemo = config.server?.allowLocalhostDemo ?? false;
|
|
1501
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1501
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1502
1502
|
app.get(
|
|
1503
1503
|
"/api/demo/session",
|
|
1504
1504
|
checkDemoOrigin(demoOrigins, allowLocalhostDemo),
|
package/dist/index.mjs
CHANGED
|
@@ -1221,7 +1221,7 @@ function createRateLimiter2(config) {
|
|
|
1221
1221
|
const limiter = createWindowBucketLimiter(6e4);
|
|
1222
1222
|
const publicLimit = config.rateLimit?.public || 60;
|
|
1223
1223
|
const privateLimit = config.rateLimit?.private || 120;
|
|
1224
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1224
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1225
1225
|
const demoApiKeys = config.rateLimit?.demoApiKeys ?? [];
|
|
1226
1226
|
return {
|
|
1227
1227
|
// Public: key is IP only
|
|
@@ -1323,7 +1323,7 @@ function isHttps(c, trustProxy) {
|
|
|
1323
1323
|
function securityHeaders(config) {
|
|
1324
1324
|
const csp = config.server?.contentSecurityPolicy || DEFAULT_CSP;
|
|
1325
1325
|
const hsts = config.server?.strictTransportSecurity ?? DEFAULT_HSTS;
|
|
1326
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1326
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1327
1327
|
return async (c, next) => {
|
|
1328
1328
|
await next();
|
|
1329
1329
|
c.header("content-security-policy", csp);
|
|
@@ -1425,7 +1425,7 @@ function demoRoutes(deps) {
|
|
|
1425
1425
|
const app = new Hono();
|
|
1426
1426
|
const demoOrigins = config.server?.allowedOrigins ?? [];
|
|
1427
1427
|
const allowLocalhostDemo = config.server?.allowLocalhostDemo ?? false;
|
|
1428
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1428
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1429
1429
|
app.get(
|
|
1430
1430
|
"/api/demo/session",
|
|
1431
1431
|
checkDemoOrigin(demoOrigins, allowLocalhostDemo),
|
|
@@ -5,11 +5,11 @@ import type { Context } from "hono";
|
|
|
5
5
|
* `X-Forwarded-For` is set by the client unless something in front of
|
|
6
6
|
* Chatter (nginx, Cloudflare, a cloud load balancer) overwrites it with the
|
|
7
7
|
* real socket address. Trusting it unconditionally lets an attacker rotate a
|
|
8
|
-
* fake value on every request and bypass per-IP limits entirely
|
|
9
|
-
* `trustProxy: true` only when such a
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
* per-client limiting.
|
|
8
|
+
* fake value on every request and bypass per-IP limits entirely, so
|
|
9
|
+
* `trustProxy` defaults to `false`: pass `trustProxy: true` only when such a
|
|
10
|
+
* proxy is guaranteed to be in front. Left `false`, every caller collapses
|
|
11
|
+
* onto one shared bucket, which is coarse but not bypassable โ pair it with
|
|
12
|
+
* a fronting proxy that does the real per-client limiting.
|
|
13
13
|
*/
|
|
14
14
|
export declare function clientRateLimitKey(c: Context, trustProxy: boolean): string;
|
|
15
15
|
//# sourceMappingURL=clientKey.d.ts.map
|
|
@@ -9,7 +9,9 @@ import type { ChatterConfig } from "../types";
|
|
|
9
9
|
* `X-Forwarded-Proto` โ see `rateLimit.trustProxy`) or `NODE_ENV=production`.
|
|
10
10
|
* A browser ignores HSTS delivered over plain HTTP (RFC 6797 ยง8.1), so this
|
|
11
11
|
* gate is about not asserting a guarantee the deployment doesn't back, not
|
|
12
|
-
* about avoiding a localhost lockout.
|
|
12
|
+
* about avoiding a localhost lockout. `trustProxy` defaults to `false`: a
|
|
13
|
+
* deployment reachable directly must opt in before a client-suppliable
|
|
14
|
+
* header is trusted for anything.
|
|
13
15
|
*
|
|
14
16
|
* Headers are set after `next()` so they still land on a handler that
|
|
15
17
|
* returns a raw `Response` (e.g. from `config.customRoutes`) rather than
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"securityHeaders.d.ts","sourceRoot":"","sources":["../../src/middleware/securityHeaders.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AAC1C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAiB9C
|
|
1
|
+
{"version":3,"file":"securityHeaders.d.ts","sourceRoot":"","sources":["../../src/middleware/securityHeaders.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AAC1C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAiB9C;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,aAAa,OAKlC,OAAO,QAAQ,IAAI,mBAQrC"}
|
package/dist/server.js
CHANGED
|
@@ -796,7 +796,7 @@ function isHttps(c, trustProxy) {
|
|
|
796
796
|
function securityHeaders(config) {
|
|
797
797
|
const csp = config.server?.contentSecurityPolicy || DEFAULT_CSP;
|
|
798
798
|
const hsts = config.server?.strictTransportSecurity ?? DEFAULT_HSTS;
|
|
799
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
799
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
800
800
|
return async (c, next) => {
|
|
801
801
|
await next();
|
|
802
802
|
c.header("content-security-policy", csp);
|
|
@@ -996,7 +996,7 @@ function demoRoutes(deps) {
|
|
|
996
996
|
const app = new import_hono.Hono();
|
|
997
997
|
const demoOrigins = config.server?.allowedOrigins ?? [];
|
|
998
998
|
const allowLocalhostDemo = config.server?.allowLocalhostDemo ?? false;
|
|
999
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
999
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1000
1000
|
app.get(
|
|
1001
1001
|
"/api/demo/session",
|
|
1002
1002
|
checkDemoOrigin(demoOrigins, allowLocalhostDemo),
|
|
@@ -1129,7 +1129,7 @@ function createRateLimiter(config) {
|
|
|
1129
1129
|
const limiter = createWindowBucketLimiter(6e4);
|
|
1130
1130
|
const publicLimit = config.rateLimit?.public || 60;
|
|
1131
1131
|
const privateLimit = config.rateLimit?.private || 120;
|
|
1132
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1132
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1133
1133
|
const demoApiKeys = config.rateLimit?.demoApiKeys ?? [];
|
|
1134
1134
|
return {
|
|
1135
1135
|
// Public: key is IP only
|
package/dist/server.mjs
CHANGED
|
@@ -761,7 +761,7 @@ function isHttps(c, trustProxy) {
|
|
|
761
761
|
function securityHeaders(config) {
|
|
762
762
|
const csp = config.server?.contentSecurityPolicy || DEFAULT_CSP;
|
|
763
763
|
const hsts = config.server?.strictTransportSecurity ?? DEFAULT_HSTS;
|
|
764
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
764
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
765
765
|
return async (c, next) => {
|
|
766
766
|
await next();
|
|
767
767
|
c.header("content-security-policy", csp);
|
|
@@ -961,7 +961,7 @@ function demoRoutes(deps) {
|
|
|
961
961
|
const app = new Hono();
|
|
962
962
|
const demoOrigins = config.server?.allowedOrigins ?? [];
|
|
963
963
|
const allowLocalhostDemo = config.server?.allowLocalhostDemo ?? false;
|
|
964
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
964
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
965
965
|
app.get(
|
|
966
966
|
"/api/demo/session",
|
|
967
967
|
checkDemoOrigin(demoOrigins, allowLocalhostDemo),
|
|
@@ -1094,7 +1094,7 @@ function createRateLimiter(config) {
|
|
|
1094
1094
|
const limiter = createWindowBucketLimiter(6e4);
|
|
1095
1095
|
const publicLimit = config.rateLimit?.public || 60;
|
|
1096
1096
|
const privateLimit = config.rateLimit?.private || 120;
|
|
1097
|
-
const trustProxy = config.rateLimit?.trustProxy ??
|
|
1097
|
+
const trustProxy = config.rateLimit?.trustProxy ?? false;
|
|
1098
1098
|
const demoApiKeys = config.rateLimit?.demoApiKeys ?? [];
|
|
1099
1099
|
return {
|
|
1100
1100
|
// Public: key is IP only
|
package/dist/types.d.ts
CHANGED
|
@@ -153,8 +153,10 @@ export interface ChatterConfig {
|
|
|
153
153
|
* Only set this when Chatter sits behind a reverse proxy (nginx,
|
|
154
154
|
* Cloudflare, a cloud load balancer) that overwrites client-supplied
|
|
155
155
|
* XFF with the real socket address โ otherwise a caller can rotate a
|
|
156
|
-
* fake value per request and bypass limits entirely. When `false
|
|
157
|
-
* every caller shares one bucket per limiter
|
|
156
|
+
* fake value per request and bypass limits entirely. When `false`
|
|
157
|
+
* (the default), every caller shares one bucket per limiter โ coarse
|
|
158
|
+
* but not spoofable, and the safe choice for a directly-exposed
|
|
159
|
+
* server. Default: false.
|
|
158
160
|
*/
|
|
159
161
|
trustProxy?: boolean;
|
|
160
162
|
/**
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED