@moxxy/sdk 0.33.0 → 0.34.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.
Files changed (90) hide show
  1. package/README.md +1 -1
  2. package/dist/audit-export.d.ts +51 -0
  3. package/dist/audit-export.d.ts.map +1 -0
  4. package/dist/audit-export.js +4 -0
  5. package/dist/audit-export.js.map +1 -0
  6. package/dist/audit.d.ts +86 -0
  7. package/dist/audit.d.ts.map +1 -0
  8. package/dist/audit.js +35 -0
  9. package/dist/audit.js.map +1 -0
  10. package/dist/define.d.ts +2 -0
  11. package/dist/define.d.ts.map +1 -1
  12. package/dist/define.js +1 -0
  13. package/dist/define.js.map +1 -1
  14. package/dist/egress.d.ts +109 -0
  15. package/dist/egress.d.ts.map +1 -0
  16. package/dist/egress.js +228 -0
  17. package/dist/egress.js.map +1 -0
  18. package/dist/events.d.ts +18 -0
  19. package/dist/events.d.ts.map +1 -1
  20. package/dist/fs-utils.d.ts +48 -0
  21. package/dist/fs-utils.d.ts.map +1 -1
  22. package/dist/fs-utils.js +114 -1
  23. package/dist/fs-utils.js.map +1 -1
  24. package/dist/hooks.d.ts +8 -0
  25. package/dist/hooks.d.ts.map +1 -1
  26. package/dist/index.d.ts +12 -0
  27. package/dist/index.d.ts.map +1 -1
  28. package/dist/index.js +8 -0
  29. package/dist/index.js.map +1 -1
  30. package/dist/plugin.d.ts +10 -0
  31. package/dist/plugin.d.ts.map +1 -1
  32. package/dist/principal-os.d.ts +14 -0
  33. package/dist/principal-os.d.ts.map +1 -0
  34. package/dist/principal-os.js +48 -0
  35. package/dist/principal-os.js.map +1 -0
  36. package/dist/principal.d.ts +54 -0
  37. package/dist/principal.d.ts.map +1 -0
  38. package/dist/principal.js +18 -0
  39. package/dist/principal.js.map +1 -0
  40. package/dist/redact.d.ts +36 -0
  41. package/dist/redact.d.ts.map +1 -0
  42. package/dist/redact.js +88 -0
  43. package/dist/redact.js.map +1 -0
  44. package/dist/schemas.d.ts +18 -18
  45. package/dist/secret-provider.d.ts +60 -0
  46. package/dist/secret-provider.d.ts.map +1 -0
  47. package/dist/secret-provider.js +59 -0
  48. package/dist/secret-provider.js.map +1 -0
  49. package/dist/server.d.ts +3 -1
  50. package/dist/server.d.ts.map +1 -1
  51. package/dist/server.js +6 -1
  52. package/dist/server.js.map +1 -1
  53. package/dist/session-like.d.ts +3 -0
  54. package/dist/session-like.d.ts.map +1 -1
  55. package/dist/signature.d.ts +21 -0
  56. package/dist/signature.d.ts.map +1 -0
  57. package/dist/signature.js +32 -0
  58. package/dist/signature.js.map +1 -0
  59. package/dist/tool-icon.d.ts +22 -0
  60. package/dist/tool-icon.d.ts.map +1 -0
  61. package/dist/tool-icon.js +44 -0
  62. package/dist/tool-icon.js.map +1 -0
  63. package/dist/tool.d.ts +8 -0
  64. package/dist/tool.d.ts.map +1 -1
  65. package/package.json +11 -4
  66. package/src/audit-export.ts +57 -0
  67. package/src/audit.ts +137 -0
  68. package/src/cross-process-lock.test.ts +23 -14
  69. package/src/define.ts +3 -0
  70. package/src/egress.test.ts +238 -0
  71. package/src/egress.ts +274 -0
  72. package/src/events.ts +18 -0
  73. package/src/fs-utils.test.ts +98 -2
  74. package/src/fs-utils.ts +120 -1
  75. package/src/hooks.ts +8 -0
  76. package/src/host-credential.test.ts +39 -0
  77. package/src/index.ts +49 -0
  78. package/src/plugin.ts +10 -0
  79. package/src/principal-os.ts +48 -0
  80. package/src/principal.test.ts +47 -0
  81. package/src/principal.ts +60 -0
  82. package/src/redact.test.ts +91 -0
  83. package/src/redact.ts +91 -0
  84. package/src/secret-provider.ts +84 -0
  85. package/src/server.ts +17 -0
  86. package/src/session-like.ts +3 -0
  87. package/src/signature.ts +34 -0
  88. package/src/tool-icon.test.ts +46 -0
  89. package/src/tool-icon.ts +46 -0
  90. package/src/tool.ts +8 -0
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  <p align="center">
2
2
  <a href="https://moxxy.ai">
3
- <img src="https://moxxy.ai/moxxy-head-256.png" alt="moxxy" width="128" />
3
+ <img src="https://raw.githubusercontent.com/moxxy-ai/moxxy/main/assets/brand/png/moxxy-mark-256.png" alt="moxxy" width="128" />
4
4
  </a>
5
5
  </p>
6
6
 
@@ -0,0 +1,51 @@
1
+ import type { AuditRecord } from './audit.js';
2
+ import type { Principal } from './principal.js';
3
+ /**
4
+ * Shipping the local audit trail somewhere central.
5
+ *
6
+ * Separate from `AuditSinkDef` on purpose. A sink is the WRITE path: it is
7
+ * handed each record as it happens. An exporter is a READER of the trail that
8
+ * has already been durably written, driven by a checkpoint.
9
+ *
10
+ * That split is what makes shipping survivable. A network sink has to decide,
11
+ * while a turn is running, what to do when the collector is down: block the
12
+ * turn, drop the record, or buffer it in memory and lose it on exit. An
13
+ * exporter has no such dilemma, because the record is already on disk in a
14
+ * hash-chained file. A failed export is retried from the checkpoint, and the
15
+ * worst case is that central visibility lags, never that the record is gone.
16
+ */
17
+ export interface AuditExportResource {
18
+ /** Which machine. The whole point of central collection is telling them apart. */
19
+ readonly host: string;
20
+ readonly cliVersion: string;
21
+ /** Whoever the surface could establish was acting; absent on an unattributed host. */
22
+ readonly principal?: Principal;
23
+ }
24
+ export interface AuditExportBatch {
25
+ readonly records: ReadonlyArray<AuditRecord>;
26
+ readonly resource: AuditExportResource;
27
+ }
28
+ export interface AuditExportContext {
29
+ /** Destination, as configured. Exporter-defined; an endpoint URL for OTLP. */
30
+ readonly endpoint: string;
31
+ /** Exporter-specific settings from `audit.export`, already placeholder-resolved. */
32
+ readonly settings: Readonly<Record<string, unknown>>;
33
+ readonly signal?: AbortSignal;
34
+ }
35
+ export interface AuditExporterDef {
36
+ readonly name: string;
37
+ readonly description?: string;
38
+ /**
39
+ * Ship one batch.
40
+ *
41
+ * THE CONTRACT: resolving means the destination has DURABLY accepted these
42
+ * records, because the checkpoint advances on resolve and those records are
43
+ * never offered again. An exporter that resolves on "request sent" turns a
44
+ * collector-side rejection into silent data loss. When in doubt, throw:
45
+ * re-sending a batch is cheap and records carry a hash the collector can
46
+ * deduplicate on, whereas a skipped batch is unrecoverable.
47
+ */
48
+ send(batch: AuditExportBatch, ctx: AuditExportContext): Promise<void>;
49
+ }
50
+ export declare function defineAuditExporter(def: AuditExporterDef): AuditExporterDef;
51
+ //# sourceMappingURL=audit-export.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-export.d.ts","sourceRoot":"","sources":["../src/audit-export.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAC9C,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAEhD;;;;;;;;;;;;;GAaG;AACH,MAAM,WAAW,mBAAmB;IAClC,kFAAkF;IAClF,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,sFAAsF;IACtF,QAAQ,CAAC,SAAS,CAAC,EAAE,SAAS,CAAC;CAChC;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,OAAO,EAAE,aAAa,CAAC,WAAW,CAAC,CAAC;IAC7C,QAAQ,CAAC,QAAQ,EAAE,mBAAmB,CAAC;CACxC;AAED,MAAM,WAAW,kBAAkB;IACjC,8EAA8E;IAC9E,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,oFAAoF;IACpF,QAAQ,CAAC,QAAQ,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;IACrD,QAAQ,CAAC,MAAM,CAAC,EAAE,WAAW,CAAC;CAC/B;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;IAC9B;;;;;;;;;OASG;IACH,IAAI,CAAC,KAAK,EAAE,gBAAgB,EAAE,GAAG,EAAE,kBAAkB,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CACvE;AAED,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,gBAAgB,GAAG,gBAAgB,CAE3E"}
@@ -0,0 +1,4 @@
1
+ export function defineAuditExporter(def) {
2
+ return def;
3
+ }
4
+ //# sourceMappingURL=audit-export.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-export.js","sourceRoot":"","sources":["../src/audit-export.ts"],"names":[],"mappings":"AAsDA,MAAM,UAAU,mBAAmB,CAAC,GAAqB;IACvD,OAAO,GAAG,CAAC;AACb,CAAC"}
@@ -0,0 +1,86 @@
1
+ import type { MoxxyEvent, MoxxyEventType } from './events.js';
2
+ import type { SessionId, TurnId } from './ids.js';
3
+ import type { Principal } from './principal.js';
4
+ /**
5
+ * The audit trail: a tamper-evident record of what the agent did, who it acted
6
+ * for, and what was allowed or denied, in a form that can LEAVE the machine.
7
+ *
8
+ * Distinct from the event log, and the distinction is the whole point. The
9
+ * event log is the conversation: complete, replayable, local, and full of
10
+ * payloads nobody wants shipped to a SIEM. An audit record is the receipt:
11
+ * bounded, redacted, hash-chained, and self-attributing, so one line is
12
+ * meaningful on its own without replaying a session to interpret it.
13
+ *
14
+ * A swappable block like every other, mirroring `EventStoreDef`: core seeds a
15
+ * protected local floor, plugins register alternatives (syslog, OTel, S3,
16
+ * webhook), and the operator activates one by name.
17
+ */
18
+ /** What kind of thing happened. Coarser than `MoxxyEventType` on purpose: an
19
+ * auditor reasons about categories of action, not about the loop's internals. */
20
+ export type AuditAction =
21
+ /** The security-relevant config in force, recorded once per session. Without
22
+ * it a trail says what was done but not what the rules were at the time,
23
+ * which is the first question asked when reviewing a past run. */
24
+ 'policy' | 'prompt' | 'tool.request' | 'tool.approved' | 'tool.denied' | 'tool.result' | 'skill.invoked' | 'skill.created' | 'plugin.registered' | 'plugin.unregistered' | 'abort'
25
+ /** Token counts for one provider call. Metadata only, never content, which
26
+ * is what makes cost attribution auditable without the trail carrying the
27
+ * conversation. */
28
+ | 'usage' | 'error' | 'other';
29
+ /**
30
+ * One record. Every field is either metadata or already-redacted, so the whole
31
+ * object is safe to forward.
32
+ */
33
+ export interface AuditRecord {
34
+ /** Position in this sink's chain. Contiguous from 0; a gap is evidence. */
35
+ readonly seq: number;
36
+ readonly ts: number;
37
+ readonly sessionId: SessionId;
38
+ readonly turnId: TurnId;
39
+ readonly action: AuditAction;
40
+ /** The underlying event type, kept so a record can be traced back. */
41
+ readonly eventType: MoxxyEventType;
42
+ /**
43
+ * Who it was done for. Absent means unattributed, which is itself worth
44
+ * auditing: it says the surface could not establish an identity.
45
+ */
46
+ readonly actor?: Principal;
47
+ /** Bounded, redacted, action-specific detail. Never raw payloads. */
48
+ readonly detail?: Readonly<Record<string, unknown>>;
49
+ /** Hash of the previous record, or null for the first. */
50
+ readonly prevHash: string | null;
51
+ /** Hash over this record's own fields plus {@link prevHash}. */
52
+ readonly hash: string;
53
+ }
54
+ /** A record before the chain fields are computed. */
55
+ export type UnchainedAuditRecord = Omit<AuditRecord, 'seq' | 'prevHash' | 'hash'>;
56
+ export interface AuditSinkScope {
57
+ readonly sessionId: SessionId;
58
+ readonly cwd: string;
59
+ }
60
+ export interface AuditSinkSession {
61
+ /**
62
+ * Append one record.
63
+ *
64
+ * Takes an UNCHAINED record: sequencing and any tamper-evidence are the
65
+ * sink's own concern, because each sink has its own ordering. The local file
66
+ * chains by day; a syslog sink has no chain at all; a remote service assigns
67
+ * its own sequence. Handing every sink a pre-sealed `seq`/`hash` would be a
68
+ * lie for all but one of them.
69
+ *
70
+ * MUST NOT throw: a failing audit sink degrades loudly, it never takes down
71
+ * the turn it is recording. Report failure by returning false.
72
+ */
73
+ write(record: UnchainedAuditRecord): Promise<boolean>;
74
+ /** Flush anything buffered. Called on session close. */
75
+ close(): Promise<void>;
76
+ }
77
+ export interface AuditSinkDef {
78
+ readonly name: string;
79
+ readonly description?: string;
80
+ open(scope: AuditSinkScope): AuditSinkSession;
81
+ }
82
+ /** Freeze an audit-sink spec, mirroring the other `defineX` factories. */
83
+ export declare function defineAuditSink(def: AuditSinkDef): AuditSinkDef;
84
+ /** The audit category for an event, or null when it is conversation only. */
85
+ export declare function auditActionOf(event: MoxxyEvent): AuditAction | null;
86
+ //# sourceMappingURL=audit.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.d.ts","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC9D,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAClD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAEhD;;;;;;;;;;;;;GAaG;AAEH;kFACkF;AAClF,MAAM,MAAM,WAAW;AACrB;;mEAEmE;AACjE,QAAQ,GACR,QAAQ,GACR,cAAc,GACd,eAAe,GACf,aAAa,GACb,aAAa,GACb,eAAe,GACf,eAAe,GACf,mBAAmB,GACnB,qBAAqB,GACrB,OAAO;AACT;;oBAEoB;GAClB,OAAO,GACP,OAAO,GACP,OAAO,CAAC;AAEZ;;;GAGG;AACH,MAAM,WAAW,WAAW;IAC1B,2EAA2E;IAC3E,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,SAAS,EAAE,SAAS,CAAC;IAC9B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,MAAM,EAAE,WAAW,CAAC;IAC7B,sEAAsE;IACtE,QAAQ,CAAC,SAAS,EAAE,cAAc,CAAC;IACnC;;;OAGG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,CAAC;IAC3B,qEAAqE;IACrE,QAAQ,CAAC,MAAM,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;IACpD,0DAA0D;IAC1D,QAAQ,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACjC,gEAAgE;IAChE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;CACvB;AAED,qDAAqD;AACrD,MAAM,MAAM,oBAAoB,GAAG,IAAI,CAAC,WAAW,EAAE,KAAK,GAAG,UAAU,GAAG,MAAM,CAAC,CAAC;AAElF,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,SAAS,EAAE,SAAS,CAAC;IAC9B,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,gBAAgB;IAC/B;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,MAAM,EAAE,oBAAoB,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtD,wDAAwD;IACxD,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CACxB;AAED,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;IAC9B,IAAI,CAAC,KAAK,EAAE,cAAc,GAAG,gBAAgB,CAAC;CAC/C;AAED,0EAA0E;AAC1E,wBAAgB,eAAe,CAAC,GAAG,EAAE,YAAY,GAAG,YAAY,CAE/D;AA6BD,6EAA6E;AAC7E,wBAAgB,aAAa,CAAC,KAAK,EAAE,UAAU,GAAG,WAAW,GAAG,IAAI,CAEnE"}
package/dist/audit.js ADDED
@@ -0,0 +1,35 @@
1
+ /** Freeze an audit-sink spec, mirroring the other `defineX` factories. */
2
+ export function defineAuditSink(def) {
3
+ return Object.freeze({ ...def });
4
+ }
5
+ /**
6
+ * Which event types produce an audit record, and under what category.
7
+ *
8
+ * Everything absent from this map is conversation, not audit: assistant text,
9
+ * reasoning, provider request/response, compaction, elision, mode iterations.
10
+ * They belong in the event log and would only bloat a trail an auditor has to
11
+ * read. Tool and permission traffic is what actually gets reviewed, so it is
12
+ * named precisely.
13
+ *
14
+ * An exhaustive map rather than a `default:` so adding an event type is a
15
+ * deliberate decision about whether it is auditable, not a silent 'other'.
16
+ */
17
+ const AUDITED = {
18
+ user_prompt: 'prompt',
19
+ tool_call_requested: 'tool.request',
20
+ tool_call_approved: 'tool.approved',
21
+ tool_call_denied: 'tool.denied',
22
+ tool_result: 'tool.result',
23
+ skill_invoked: 'skill.invoked',
24
+ skill_created: 'skill.created',
25
+ plugin_registered: 'plugin.registered',
26
+ plugin_unregistered: 'plugin.unregistered',
27
+ abort: 'abort',
28
+ provider_response: 'usage',
29
+ error: 'error',
30
+ };
31
+ /** The audit category for an event, or null when it is conversation only. */
32
+ export function auditActionOf(event) {
33
+ return AUDITED[event.type] ?? null;
34
+ }
35
+ //# sourceMappingURL=audit.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.js","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"AAqGA,0EAA0E;AAC1E,MAAM,UAAU,eAAe,CAAC,GAAiB;IAC/C,OAAO,MAAM,CAAC,MAAM,CAAC,EAAE,GAAG,GAAG,EAAE,CAAC,CAAC;AACnC,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,OAAO,GAAiD;IAC5D,WAAW,EAAE,QAAQ;IACrB,mBAAmB,EAAE,cAAc;IACnC,kBAAkB,EAAE,eAAe;IACnC,gBAAgB,EAAE,aAAa;IAC/B,WAAW,EAAE,aAAa;IAC1B,aAAa,EAAE,eAAe;IAC9B,aAAa,EAAE,eAAe;IAC9B,iBAAiB,EAAE,mBAAmB;IACtC,mBAAmB,EAAE,qBAAqB;IAC1C,KAAK,EAAE,OAAO;IACd,iBAAiB,EAAE,OAAO;IAC1B,KAAK,EAAE,OAAO;CACf,CAAC;AAEF,6EAA6E;AAC7E,MAAM,UAAU,aAAa,CAAC,KAAiB;IAC7C,OAAO,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC;AACrC,CAAC"}
package/dist/define.d.ts CHANGED
@@ -9,6 +9,7 @@ import type { PermissionRule } from './permission.js';
9
9
  import type { Plugin, PluginSpec } from './plugin.js';
10
10
  import type { ProviderDef } from './provider.js';
11
11
  import type { SkillDef, SkillFrontmatter } from './skill.js';
12
+ import type { ToolIcon } from './tool-icon.js';
12
13
  import type { HostedTool, ToolCompactPresentation, ToolContext, ToolDef } from './tool.js';
13
14
  import type { ToolIsolationSpec } from './isolation.js';
14
15
  import type { TranscriberDef } from './transcriber.js';
@@ -35,6 +36,7 @@ export declare function defineTool<S extends z.ZodTypeAny, O = unknown>(spec: {
35
36
  permission?: PermissionRule;
36
37
  handler: (input: z.output<S>, ctx: ToolContext) => Promise<O> | O;
37
38
  compact?: ToolCompactPresentation;
39
+ icon?: ToolIcon;
38
40
  isolation?: ToolIsolationSpec;
39
41
  }): ToolDef;
40
42
  export declare function defineProvider(spec: ProviderDef): ProviderDef;
@@ -1 +1 @@
1
- {"version":3,"file":"define.d.ts","sourceRoot":"","sources":["../src/define.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"define.d.ts","sourceRoot":"","sources":["../src/define.ts"],"names":[],"mappings":"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"}
package/dist/define.js CHANGED
@@ -26,6 +26,7 @@ export function defineTool(spec) {
26
26
  permission: spec.permission,
27
27
  handler: spec.handler,
28
28
  compact: spec.compact,
29
+ icon: spec.icon,
29
30
  isolation: spec.isolation,
30
31
  });
31
32
  }
@@ -1 +1 @@
1
- {"version":3,"file":"define.js","sourceRoot":"","sources":["../src/define.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"define.js","sourceRoot":"","sources":["../src/define.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,109 @@
1
+ /**
2
+ * Outbound HTTP egress: corporate proxy support for everything moxxy fetches.
3
+ *
4
+ * Node's global `fetch` ignores `HTTPS_PROXY` entirely, and every provider
5
+ * reaches its API through it (`@anthropic-ai/sdk`, `openai`, and the plain
6
+ * `fetch` calls in tools). On a network that requires an outbound proxy that
7
+ * means the first provider call fails with an opaque network error and there is
8
+ * no setting that fixes it. Installing a global undici dispatcher is the only
9
+ * way to route global `fetch` through a proxy.
10
+ *
11
+ * `undici` is imported DYNAMICALLY and only when a proxy is actually configured,
12
+ * so `@moxxy/sdk` keeps zero hard runtime dependencies and a host with no proxy
13
+ * pays nothing. The package is a real dependency of `@moxxy/cli`.
14
+ *
15
+ * Not handled here, on purpose: a corporate TLS-terminating CA is Node's job,
16
+ * via `NODE_EXTRA_CA_CERTS=/path/to/ca.pem` in the environment before Node
17
+ * starts. There is no in-process equivalent, so the doctor surfaces whether it
18
+ * is set rather than pretending to configure it.
19
+ */
20
+ /** Proxy inputs, already resolved from env and/or config. */
21
+ export interface EgressProxySettings {
22
+ /** Proxy for `http:` origins. */
23
+ readonly httpProxy?: string;
24
+ /** Proxy for `https:` origins. */
25
+ readonly httpsProxy?: string;
26
+ /** Raw `NO_PROXY` value: comma/whitespace separated bypass rules. */
27
+ readonly noProxy?: string;
28
+ }
29
+ export interface EgressStatus {
30
+ /** True when a global dispatcher was installed. */
31
+ readonly enabled: boolean;
32
+ /** Credential-redacted proxy in use for `http:`, when set. */
33
+ readonly httpProxy?: string;
34
+ /** Credential-redacted proxy in use for `https:`, when set. */
35
+ readonly httpsProxy?: string;
36
+ /** Parsed bypass rules. */
37
+ readonly noProxy?: ReadonlyArray<string>;
38
+ /** Why nothing was installed, or why installation failed. */
39
+ readonly reason?: string;
40
+ }
41
+ /**
42
+ * Read proxy settings from an environment. Lowercase wins over uppercase, which
43
+ * is the de-facto convention (curl, requests, Go): a shell that exports both
44
+ * usually means the lowercase one was set deliberately and more recently.
45
+ *
46
+ * `http_proxy` is deliberately NOT used as a fallback for https origins. Some
47
+ * environments set only `http_proxy` for a plaintext-only proxy, and silently
48
+ * tunnelling TLS through it would fail confusingly rather than going direct.
49
+ */
50
+ export declare function readProxyEnv(env?: Readonly<Record<string, string | undefined>>): EgressProxySettings;
51
+ /** Split a `NO_PROXY` value into normalized rules. Separators are commas and
52
+ * whitespace; empty entries are dropped and matching is case-insensitive. */
53
+ export declare function parseNoProxy(value: string | undefined): string[];
54
+ /**
55
+ * Whether `origin` bypasses the proxy under `rules` (already parsed by
56
+ * {@link parseNoProxy}).
57
+ *
58
+ * Follows the de-facto `NO_PROXY` convention rather than inventing one:
59
+ * - `*` bypasses everything.
60
+ * - a bare host matches that host exactly, on any port.
61
+ * - a leading `.` or `*.` matches the domain and every subdomain, so
62
+ * `.corp.example` covers `api.corp.example` AND `corp.example`.
63
+ * - an entry carrying `:port` matches only that port; the origin's port is
64
+ * resolved from the scheme when the URL omits it.
65
+ *
66
+ * A malformed origin never bypasses: failing closed here sends the request
67
+ * through the proxy, which an operator can observe, rather than silently
68
+ * leaking it direct.
69
+ */
70
+ export declare function shouldBypassProxy(origin: string, rules: ReadonlyArray<string>): boolean;
71
+ /**
72
+ * A proxy URL with any embedded credentials masked, safe to log or show in
73
+ * `moxxy doctor`. Proxy URLs routinely carry `user:password@`, and this string
74
+ * ends up on terminals and in support pastes.
75
+ */
76
+ export declare function redactProxyUrl(value: string): string;
77
+ /** True when at least one proxy is configured, i.e. there is work to do. */
78
+ export declare function hasProxy(settings: EgressProxySettings): boolean;
79
+ interface UndiciModule {
80
+ readonly Agent: new (opts?: unknown) => UndiciDispatcher;
81
+ readonly ProxyAgent: new (opts: {
82
+ uri: string;
83
+ }) => UndiciDispatcher;
84
+ readonly setGlobalDispatcher: (dispatcher: UndiciDispatcher) => void;
85
+ }
86
+ interface UndiciDispatcher {
87
+ dispatch(opts: {
88
+ origin?: string | URL;
89
+ }, handler: unknown): boolean;
90
+ close(): Promise<void>;
91
+ destroy(): Promise<void>;
92
+ }
93
+ export interface InstallEgressProxyOptions {
94
+ /** Surface for the "configured but unusable" case. Defaults to stderr. */
95
+ readonly warn?: (message: string) => void;
96
+ /** Injectable module loader for tests. */
97
+ readonly loadUndici?: () => Promise<UndiciModule>;
98
+ }
99
+ /**
100
+ * Install a global dispatcher routing outbound requests through the configured
101
+ * proxy, honouring the bypass rules. No-ops (and reports why) when no proxy is
102
+ * configured, so this is safe to call unconditionally at boot.
103
+ *
104
+ * Never throws: a broken proxy setting must degrade to a loud warning plus
105
+ * direct connections, not a failed boot.
106
+ */
107
+ export declare function installEgressProxy(settings: EgressProxySettings, opts?: InstallEgressProxyOptions): Promise<EgressStatus>;
108
+ export {};
109
+ //# sourceMappingURL=egress.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"egress.d.ts","sourceRoot":"","sources":["../src/egress.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;GAkBG;AAEH,6DAA6D;AAC7D,MAAM,WAAW,mBAAmB;IAClC,iCAAiC;IACjC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,kCAAkC;IAClC,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;IAC7B,qEAAqE;IACrE,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAC;CAC3B;AAED,MAAM,WAAW,YAAY;IAC3B,mDAAmD;IACnD,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAC1B,8DAA8D;IAC9D,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,+DAA+D;IAC/D,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;IAC7B,2BAA2B;IAC3B,QAAQ,CAAC,OAAO,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,CAAC;IACzC,6DAA6D;IAC7D,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;;;;GAQG;AACH,wBAAgB,YAAY,CAC1B,GAAG,GAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CAAe,GAC9D,mBAAmB,CAarB;AAED;8EAC8E;AAC9E,wBAAgB,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,EAAE,CAMhE;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,aAAa,CAAC,MAAM,CAAC,GAAG,OAAO,CA+BvF;AA4BD;;;;GAIG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAWpD;AAED,4EAA4E;AAC5E,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,mBAAmB,GAAG,OAAO,CAE/D;AAED,UAAU,YAAY;IACpB,QAAQ,CAAC,KAAK,EAAE,KAAK,IAAI,CAAC,EAAE,OAAO,KAAK,gBAAgB,CAAC;IACzD,QAAQ,CAAC,UAAU,EAAE,KAAK,IAAI,EAAE;QAAE,GAAG,EAAE,MAAM,CAAA;KAAE,KAAK,gBAAgB,CAAC;IACrE,QAAQ,CAAC,mBAAmB,EAAE,CAAC,UAAU,EAAE,gBAAgB,KAAK,IAAI,CAAC;CACtE;AAED,UAAU,gBAAgB;IACxB,QAAQ,CAAC,IAAI,EAAE;QAAE,MAAM,CAAC,EAAE,MAAM,GAAG,GAAG,CAAA;KAAE,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC;IACrE,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;IACvB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CAC1B;AAED,MAAM,WAAW,yBAAyB;IACxC,0EAA0E;IAC1E,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,0CAA0C;IAC1C,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,OAAO,CAAC,YAAY,CAAC,CAAC;CACnD;AAED;;;;;;;GAOG;AACH,wBAAsB,kBAAkB,CACtC,QAAQ,EAAE,mBAAmB,EAC7B,IAAI,GAAE,yBAA8B,GACnC,OAAO,CAAC,YAAY,CAAC,CA8DvB"}
package/dist/egress.js ADDED
@@ -0,0 +1,228 @@
1
+ /**
2
+ * Outbound HTTP egress: corporate proxy support for everything moxxy fetches.
3
+ *
4
+ * Node's global `fetch` ignores `HTTPS_PROXY` entirely, and every provider
5
+ * reaches its API through it (`@anthropic-ai/sdk`, `openai`, and the plain
6
+ * `fetch` calls in tools). On a network that requires an outbound proxy that
7
+ * means the first provider call fails with an opaque network error and there is
8
+ * no setting that fixes it. Installing a global undici dispatcher is the only
9
+ * way to route global `fetch` through a proxy.
10
+ *
11
+ * `undici` is imported DYNAMICALLY and only when a proxy is actually configured,
12
+ * so `@moxxy/sdk` keeps zero hard runtime dependencies and a host with no proxy
13
+ * pays nothing. The package is a real dependency of `@moxxy/cli`.
14
+ *
15
+ * Not handled here, on purpose: a corporate TLS-terminating CA is Node's job,
16
+ * via `NODE_EXTRA_CA_CERTS=/path/to/ca.pem` in the environment before Node
17
+ * starts. There is no in-process equivalent, so the doctor surfaces whether it
18
+ * is set rather than pretending to configure it.
19
+ */
20
+ /**
21
+ * Read proxy settings from an environment. Lowercase wins over uppercase, which
22
+ * is the de-facto convention (curl, requests, Go): a shell that exports both
23
+ * usually means the lowercase one was set deliberately and more recently.
24
+ *
25
+ * `http_proxy` is deliberately NOT used as a fallback for https origins. Some
26
+ * environments set only `http_proxy` for a plaintext-only proxy, and silently
27
+ * tunnelling TLS through it would fail confusingly rather than going direct.
28
+ */
29
+ export function readProxyEnv(env = process.env) {
30
+ const pick = (lower, upper) => {
31
+ const value = (env[lower] ?? env[upper] ?? '').trim();
32
+ return value.length > 0 ? value : undefined;
33
+ };
34
+ const httpProxy = pick('http_proxy', 'HTTP_PROXY');
35
+ const httpsProxy = pick('https_proxy', 'HTTPS_PROXY');
36
+ const noProxy = pick('no_proxy', 'NO_PROXY');
37
+ return {
38
+ ...(httpProxy ? { httpProxy } : {}),
39
+ ...(httpsProxy ? { httpsProxy } : {}),
40
+ ...(noProxy ? { noProxy } : {}),
41
+ };
42
+ }
43
+ /** Split a `NO_PROXY` value into normalized rules. Separators are commas and
44
+ * whitespace; empty entries are dropped and matching is case-insensitive. */
45
+ export function parseNoProxy(value) {
46
+ if (!value)
47
+ return [];
48
+ return value
49
+ .split(/[,\s]+/)
50
+ .map((rule) => rule.trim().toLowerCase())
51
+ .filter((rule) => rule.length > 0);
52
+ }
53
+ /**
54
+ * Whether `origin` bypasses the proxy under `rules` (already parsed by
55
+ * {@link parseNoProxy}).
56
+ *
57
+ * Follows the de-facto `NO_PROXY` convention rather than inventing one:
58
+ * - `*` bypasses everything.
59
+ * - a bare host matches that host exactly, on any port.
60
+ * - a leading `.` or `*.` matches the domain and every subdomain, so
61
+ * `.corp.example` covers `api.corp.example` AND `corp.example`.
62
+ * - an entry carrying `:port` matches only that port; the origin's port is
63
+ * resolved from the scheme when the URL omits it.
64
+ *
65
+ * A malformed origin never bypasses: failing closed here sends the request
66
+ * through the proxy, which an operator can observe, rather than silently
67
+ * leaking it direct.
68
+ */
69
+ export function shouldBypassProxy(origin, rules) {
70
+ if (rules.length === 0)
71
+ return false;
72
+ if (rules.includes('*'))
73
+ return true;
74
+ let url;
75
+ try {
76
+ url = new URL(origin);
77
+ }
78
+ catch {
79
+ return false;
80
+ }
81
+ const host = url.hostname.toLowerCase().replace(/^\[|\]$/g, '');
82
+ const port = url.port || (url.protocol === 'https:' ? '443' : '80');
83
+ for (const rule of rules) {
84
+ const { host: ruleHost, port: rulePort } = splitRule(rule);
85
+ if (rulePort !== undefined && rulePort !== port)
86
+ continue;
87
+ if (ruleHost.length === 0)
88
+ continue;
89
+ const suffix = ruleHost.startsWith('*.')
90
+ ? ruleHost.slice(1)
91
+ : ruleHost.startsWith('.')
92
+ ? ruleHost
93
+ : undefined;
94
+ if (suffix) {
95
+ // `.corp.example` covers the apex too, matching curl.
96
+ if (host === suffix.slice(1) || host.endsWith(suffix))
97
+ return true;
98
+ continue;
99
+ }
100
+ if (host === ruleHost)
101
+ return true;
102
+ }
103
+ return false;
104
+ }
105
+ /**
106
+ * Split a bypass rule into host and optional port.
107
+ *
108
+ * A bare IPv6 literal contains colons of its own, so `::1` must not be read as
109
+ * host `:` on port `1`. As in a URL, a port qualifier on an IPv6 address
110
+ * requires brackets (`[::1]:7000`); an unbracketed rule with more than one
111
+ * colon is therefore an address, never a host:port pair.
112
+ */
113
+ function splitRule(rule) {
114
+ if (rule.startsWith('[')) {
115
+ const end = rule.indexOf(']');
116
+ if (end === -1)
117
+ return { host: rule.slice(1) };
118
+ const host = rule.slice(1, end);
119
+ const rest = rule.slice(end + 1);
120
+ return rest.startsWith(':') && /^\d+$/.test(rest.slice(1))
121
+ ? { host, port: rest.slice(1) }
122
+ : { host };
123
+ }
124
+ const first = rule.indexOf(':');
125
+ if (first === -1 || first !== rule.lastIndexOf(':'))
126
+ return { host: rule };
127
+ const maybePort = rule.slice(first + 1);
128
+ return /^\d+$/.test(maybePort)
129
+ ? { host: rule.slice(0, first), port: maybePort }
130
+ : { host: rule };
131
+ }
132
+ /**
133
+ * A proxy URL with any embedded credentials masked, safe to log or show in
134
+ * `moxxy doctor`. Proxy URLs routinely carry `user:password@`, and this string
135
+ * ends up on terminals and in support pastes.
136
+ */
137
+ export function redactProxyUrl(value) {
138
+ try {
139
+ const url = new URL(value);
140
+ if (!url.username && !url.password)
141
+ return url.toString();
142
+ url.username = url.username ? '***' : '';
143
+ url.password = url.password ? '***' : '';
144
+ return url.toString();
145
+ }
146
+ catch {
147
+ // Unparseable: reveal nothing rather than echoing a possible secret.
148
+ return '<invalid proxy url>';
149
+ }
150
+ }
151
+ /** True when at least one proxy is configured, i.e. there is work to do. */
152
+ export function hasProxy(settings) {
153
+ return Boolean(settings.httpProxy ?? settings.httpsProxy);
154
+ }
155
+ /**
156
+ * Install a global dispatcher routing outbound requests through the configured
157
+ * proxy, honouring the bypass rules. No-ops (and reports why) when no proxy is
158
+ * configured, so this is safe to call unconditionally at boot.
159
+ *
160
+ * Never throws: a broken proxy setting must degrade to a loud warning plus
161
+ * direct connections, not a failed boot.
162
+ */
163
+ export async function installEgressProxy(settings, opts = {}) {
164
+ if (!hasProxy(settings))
165
+ return { enabled: false, reason: 'no proxy configured' };
166
+ const warn = opts.warn ?? ((m) => process.stderr.write(`[moxxy] ${m}\n`));
167
+ for (const [label, value] of [
168
+ ['http_proxy', settings.httpProxy],
169
+ ['https_proxy', settings.httpsProxy],
170
+ ]) {
171
+ if (value === undefined)
172
+ continue;
173
+ try {
174
+ new URL(value);
175
+ }
176
+ catch {
177
+ const reason = `${label} is not a valid URL; continuing without a proxy`;
178
+ warn(reason);
179
+ return { enabled: false, reason };
180
+ }
181
+ }
182
+ let undici;
183
+ try {
184
+ undici = await (opts.loadUndici ?? defaultLoadUndici)();
185
+ }
186
+ catch {
187
+ const reason = 'a proxy is configured but the `undici` package is unavailable; ' +
188
+ 'outbound requests will bypass it and may fail';
189
+ warn(reason);
190
+ return { enabled: false, reason };
191
+ }
192
+ const rules = parseNoProxy(settings.noProxy);
193
+ const direct = new undici.Agent();
194
+ const httpProxy = settings.httpProxy ? new undici.ProxyAgent({ uri: settings.httpProxy }) : undefined;
195
+ const httpsProxy = settings.httpsProxy
196
+ ? new undici.ProxyAgent({ uri: settings.httpsProxy })
197
+ : undefined;
198
+ const route = (origin) => {
199
+ if (origin === undefined)
200
+ return direct;
201
+ const href = typeof origin === 'string' ? origin : origin.href;
202
+ if (shouldBypassProxy(href, rules))
203
+ return direct;
204
+ const secure = href.startsWith('https:');
205
+ return (secure ? httpsProxy : httpProxy) ?? direct;
206
+ };
207
+ const all = [direct, httpProxy, httpsProxy].filter(Boolean);
208
+ const router = {
209
+ dispatch: (dispatchOpts, handler) => route(dispatchOpts.origin).dispatch(dispatchOpts, handler),
210
+ close: async () => {
211
+ await Promise.all(all.map((d) => d.close()));
212
+ },
213
+ destroy: async () => {
214
+ await Promise.all(all.map((d) => d.destroy()));
215
+ },
216
+ };
217
+ undici.setGlobalDispatcher(router);
218
+ return {
219
+ enabled: true,
220
+ ...(settings.httpProxy ? { httpProxy: redactProxyUrl(settings.httpProxy) } : {}),
221
+ ...(settings.httpsProxy ? { httpsProxy: redactProxyUrl(settings.httpsProxy) } : {}),
222
+ ...(rules.length > 0 ? { noProxy: rules } : {}),
223
+ };
224
+ }
225
+ async function defaultLoadUndici() {
226
+ return (await import('undici'));
227
+ }
228
+ //# sourceMappingURL=egress.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"egress.js","sourceRoot":"","sources":["../src/egress.ts"],"names":[],"mappings":"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"}
package/dist/events.d.ts CHANGED
@@ -1,4 +1,5 @@
1
1
  import type { EventId, PluginId, SessionId, SkillId, ToolCallId, TurnId } from './ids.js';
2
+ import type { Principal } from './principal.js';
2
3
  export type EventSource = 'user' | 'model' | 'tool' | 'plugin' | 'system' | 'compactor';
3
4
  export interface EventBase {
4
5
  readonly id: EventId;
@@ -8,6 +9,23 @@ export interface EventBase {
8
9
  readonly turnId: TurnId;
9
10
  readonly causationId?: EventId;
10
11
  readonly source: EventSource;
12
+ /**
13
+ * Who the action was taken on behalf of. `source` is a CATEGORY (user, model,
14
+ * tool, …); this is the SUBJECT, and without it a transcript proves a machine
15
+ * did something rather than that a person did.
16
+ *
17
+ * Stamped on EVERY event, not only turn boundaries, and carrying the whole
18
+ * principal rather than a reference. That repeats ~55 bytes per event, which
19
+ * is small against an envelope that already carries three ULIDs, and it buys
20
+ * the property an audit sink needs: a single record is self-attributing, so
21
+ * shipping one line to a SIEM requires no fold and no join. This is the same
22
+ * trade CloudTrail and the Kubernetes audit log make.
23
+ *
24
+ * OPTIONAL because the log is append-only and persisted: sessions recorded
25
+ * before identity existed replay with no actor, and must keep replaying.
26
+ * Treat absent as "unattributed", never as an error.
27
+ */
28
+ readonly actor?: Principal;
11
29
  }
12
30
  export interface UserPromptAttachment {
13
31
  readonly kind: 'stdin' | 'file' | 'image' | 'document' | 'audio';