@tickernelz/paperclip-pro-adapter-claude-local 2026.925.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 (206) hide show
  1. package/LICENSE +22 -0
  2. package/dist/cli/format-event.d.ts +2 -0
  3. package/dist/cli/format-event.d.ts.map +1 -0
  4. package/dist/cli/format-event.js +141 -0
  5. package/dist/cli/format-event.js.map +1 -0
  6. package/dist/cli/index.d.ts +2 -0
  7. package/dist/cli/index.d.ts.map +1 -0
  8. package/dist/cli/index.js +2 -0
  9. package/dist/cli/index.js.map +1 -0
  10. package/dist/cli/quota-probe.d.ts +3 -0
  11. package/dist/cli/quota-probe.d.ts.map +1 -0
  12. package/dist/cli/quota-probe.js +106 -0
  13. package/dist/cli/quota-probe.js.map +1 -0
  14. package/dist/index.d.ts +13 -0
  15. package/dist/index.d.ts.map +1 -0
  16. package/dist/index.js +90 -0
  17. package/dist/index.js.map +1 -0
  18. package/dist/index.test.d.ts +2 -0
  19. package/dist/index.test.d.ts.map +1 -0
  20. package/dist/index.test.js +35 -0
  21. package/dist/index.test.js.map +1 -0
  22. package/dist/server/acp.auth.test.d.ts +2 -0
  23. package/dist/server/acp.auth.test.d.ts.map +1 -0
  24. package/dist/server/acp.auth.test.js +581 -0
  25. package/dist/server/acp.auth.test.js.map +1 -0
  26. package/dist/server/acp.d.ts +68 -0
  27. package/dist/server/acp.d.ts.map +1 -0
  28. package/dist/server/acp.js +779 -0
  29. package/dist/server/acp.js.map +1 -0
  30. package/dist/server/acp.quota.test.d.ts +2 -0
  31. package/dist/server/acp.quota.test.d.ts.map +1 -0
  32. package/dist/server/acp.quota.test.js +114 -0
  33. package/dist/server/acp.quota.test.js.map +1 -0
  34. package/dist/server/acp.test.d.ts +2 -0
  35. package/dist/server/acp.test.d.ts.map +1 -0
  36. package/dist/server/acp.test.js +1153 -0
  37. package/dist/server/acp.test.js.map +1 -0
  38. package/dist/server/auth-check.d.ts +8 -0
  39. package/dist/server/auth-check.d.ts.map +1 -0
  40. package/dist/server/auth-check.js +8 -0
  41. package/dist/server/auth-check.js.map +1 -0
  42. package/dist/server/claude-config.d.ts +49 -0
  43. package/dist/server/claude-config.d.ts.map +1 -0
  44. package/dist/server/claude-config.js +279 -0
  45. package/dist/server/claude-config.js.map +1 -0
  46. package/dist/server/claude-config.test.d.ts +2 -0
  47. package/dist/server/claude-config.test.d.ts.map +1 -0
  48. package/dist/server/claude-config.test.js +197 -0
  49. package/dist/server/claude-config.test.js.map +1 -0
  50. package/dist/server/cli-capabilities.d.ts +26 -0
  51. package/dist/server/cli-capabilities.d.ts.map +1 -0
  52. package/dist/server/cli-capabilities.js +115 -0
  53. package/dist/server/cli-capabilities.js.map +1 -0
  54. package/dist/server/config-schema.d.ts +3 -0
  55. package/dist/server/config-schema.d.ts.map +1 -0
  56. package/dist/server/config-schema.js +67 -0
  57. package/dist/server/config-schema.js.map +1 -0
  58. package/dist/server/engine-availability.test.d.ts +2 -0
  59. package/dist/server/engine-availability.test.d.ts.map +1 -0
  60. package/dist/server/engine-availability.test.js +41 -0
  61. package/dist/server/engine-availability.test.js.map +1 -0
  62. package/dist/server/execute.acp-fallback.test.d.ts +2 -0
  63. package/dist/server/execute.acp-fallback.test.d.ts.map +1 -0
  64. package/dist/server/execute.acp-fallback.test.js +104 -0
  65. package/dist/server/execute.acp-fallback.test.js.map +1 -0
  66. package/dist/server/execute.d.ts +23 -0
  67. package/dist/server/execute.d.ts.map +1 -0
  68. package/dist/server/execute.js +1089 -0
  69. package/dist/server/execute.js.map +1 -0
  70. package/dist/server/execute.remote.test.d.ts +2 -0
  71. package/dist/server/execute.remote.test.d.ts.map +1 -0
  72. package/dist/server/execute.remote.test.js +484 -0
  73. package/dist/server/execute.remote.test.js.map +1 -0
  74. package/dist/server/index.d.ts +16 -0
  75. package/dist/server/index.d.ts.map +1 -0
  76. package/dist/server/index.js +84 -0
  77. package/dist/server/index.js.map +1 -0
  78. package/dist/server/models.d.ts +13 -0
  79. package/dist/server/models.d.ts.map +1 -0
  80. package/dist/server/models.js +153 -0
  81. package/dist/server/models.js.map +1 -0
  82. package/dist/server/parse.d.ts +58 -0
  83. package/dist/server/parse.d.ts.map +1 -0
  84. package/dist/server/parse.js +459 -0
  85. package/dist/server/parse.js.map +1 -0
  86. package/dist/server/parse.test.d.ts +2 -0
  87. package/dist/server/parse.test.d.ts.map +1 -0
  88. package/dist/server/parse.test.js +419 -0
  89. package/dist/server/parse.test.js.map +1 -0
  90. package/dist/server/permissions.d.ts +14 -0
  91. package/dist/server/permissions.d.ts.map +1 -0
  92. package/dist/server/permissions.js +13 -0
  93. package/dist/server/permissions.js.map +1 -0
  94. package/dist/server/permissions.test.d.ts +2 -0
  95. package/dist/server/permissions.test.d.ts.map +1 -0
  96. package/dist/server/permissions.test.js +22 -0
  97. package/dist/server/permissions.test.js.map +1 -0
  98. package/dist/server/probe-diagnostics.d.ts +102 -0
  99. package/dist/server/probe-diagnostics.d.ts.map +1 -0
  100. package/dist/server/probe-diagnostics.js +140 -0
  101. package/dist/server/probe-diagnostics.js.map +1 -0
  102. package/dist/server/probe-diagnostics.test.d.ts +2 -0
  103. package/dist/server/probe-diagnostics.test.d.ts.map +1 -0
  104. package/dist/server/probe-diagnostics.test.js +114 -0
  105. package/dist/server/probe-diagnostics.test.js.map +1 -0
  106. package/dist/server/probe-env.d.ts +42 -0
  107. package/dist/server/probe-env.d.ts.map +1 -0
  108. package/dist/server/probe-env.js +149 -0
  109. package/dist/server/probe-env.js.map +1 -0
  110. package/dist/server/probe-env.test.d.ts +2 -0
  111. package/dist/server/probe-env.test.d.ts.map +1 -0
  112. package/dist/server/probe-env.test.js +135 -0
  113. package/dist/server/probe-env.test.js.map +1 -0
  114. package/dist/server/probe-redaction.test.d.ts +2 -0
  115. package/dist/server/probe-redaction.test.d.ts.map +1 -0
  116. package/dist/server/probe-redaction.test.js +86 -0
  117. package/dist/server/probe-redaction.test.js.map +1 -0
  118. package/dist/server/prompt-cache.d.ts +17 -0
  119. package/dist/server/prompt-cache.d.ts.map +1 -0
  120. package/dist/server/prompt-cache.js +126 -0
  121. package/dist/server/prompt-cache.js.map +1 -0
  122. package/dist/server/quota-keychain.test.d.ts +2 -0
  123. package/dist/server/quota-keychain.test.d.ts.map +1 -0
  124. package/dist/server/quota-keychain.test.js +83 -0
  125. package/dist/server/quota-keychain.test.js.map +1 -0
  126. package/dist/server/quota.d.ts +30 -0
  127. package/dist/server/quota.d.ts.map +1 -0
  128. package/dist/server/quota.js +543 -0
  129. package/dist/server/quota.js.map +1 -0
  130. package/dist/server/setup-token-characterization.test.d.ts +2 -0
  131. package/dist/server/setup-token-characterization.test.d.ts.map +1 -0
  132. package/dist/server/setup-token-characterization.test.js +123 -0
  133. package/dist/server/setup-token-characterization.test.js.map +1 -0
  134. package/dist/server/setup-token-parse.d.ts +47 -0
  135. package/dist/server/setup-token-parse.d.ts.map +1 -0
  136. package/dist/server/setup-token-parse.js +506 -0
  137. package/dist/server/setup-token-parse.js.map +1 -0
  138. package/dist/server/setup-token-parse.test.d.ts +2 -0
  139. package/dist/server/setup-token-parse.test.d.ts.map +1 -0
  140. package/dist/server/setup-token-parse.test.js +587 -0
  141. package/dist/server/setup-token-parse.test.js.map +1 -0
  142. package/dist/server/setup-token-runner.d.ts +115 -0
  143. package/dist/server/setup-token-runner.d.ts.map +1 -0
  144. package/dist/server/setup-token-runner.js +317 -0
  145. package/dist/server/setup-token-runner.js.map +1 -0
  146. package/dist/server/setup-token-runner.test.d.ts +2 -0
  147. package/dist/server/setup-token-runner.test.d.ts.map +1 -0
  148. package/dist/server/setup-token-runner.test.js +336 -0
  149. package/dist/server/setup-token-runner.test.js.map +1 -0
  150. package/dist/server/skills.d.ts +8 -0
  151. package/dist/server/skills.d.ts.map +1 -0
  152. package/dist/server/skills.js +42 -0
  153. package/dist/server/skills.js.map +1 -0
  154. package/dist/server/test.d.ts +3 -0
  155. package/dist/server/test.d.ts.map +1 -0
  156. package/dist/server/test.js +434 -0
  157. package/dist/server/test.js.map +1 -0
  158. package/dist/server/test.probe.test.d.ts +2 -0
  159. package/dist/server/test.probe.test.d.ts.map +1 -0
  160. package/dist/server/test.probe.test.js +608 -0
  161. package/dist/server/test.probe.test.js.map +1 -0
  162. package/dist/server/test.remote.test.d.ts +2 -0
  163. package/dist/server/test.remote.test.d.ts.map +1 -0
  164. package/dist/server/test.remote.test.js +149 -0
  165. package/dist/server/test.remote.test.js.map +1 -0
  166. package/dist/ui/build-config.d.ts +3 -0
  167. package/dist/ui/build-config.d.ts.map +1 -0
  168. package/dist/ui/build-config.js +76 -0
  169. package/dist/ui/build-config.js.map +1 -0
  170. package/dist/ui/build-config.test.d.ts +2 -0
  171. package/dist/ui/build-config.test.d.ts.map +1 -0
  172. package/dist/ui/build-config.test.js +68 -0
  173. package/dist/ui/build-config.test.js.map +1 -0
  174. package/dist/ui/index.d.ts +3 -0
  175. package/dist/ui/index.d.ts.map +1 -0
  176. package/dist/ui/index.js +3 -0
  177. package/dist/ui/index.js.map +1 -0
  178. package/dist/ui/parse-stdout.d.ts +3 -0
  179. package/dist/ui/parse-stdout.d.ts.map +1 -0
  180. package/dist/ui/parse-stdout.js +153 -0
  181. package/dist/ui/parse-stdout.js.map +1 -0
  182. package/package.json +63 -0
  183. package/skills/agentmail/SKILL.md +70 -0
  184. package/skills/paperclip/SKILL.md +712 -0
  185. package/skills/paperclip/references/api-reference.md +1675 -0
  186. package/skills/paperclip/references/artifacts.md +158 -0
  187. package/skills/paperclip/references/cases.md +295 -0
  188. package/skills/paperclip/references/company-skills.md +266 -0
  189. package/skills/paperclip/references/issue-workspaces.md +80 -0
  190. package/skills/paperclip/references/routines.md +231 -0
  191. package/skills/paperclip/references/workflows.md +141 -0
  192. package/skills/paperclip/scripts/paperclip-upload-artifact.sh +592 -0
  193. package/skills/paperclip-board/SKILL.md +619 -0
  194. package/skills/paperclip-converting-plans-to-tasks/SKILL.md +60 -0
  195. package/skills/paperclip-create-agent/SKILL.md +179 -0
  196. package/skills/paperclip-create-agent/references/agent-instruction-templates.md +123 -0
  197. package/skills/paperclip-create-agent/references/agents/coder.md +64 -0
  198. package/skills/paperclip-create-agent/references/agents/qa.md +88 -0
  199. package/skills/paperclip-create-agent/references/agents/securityengineer.md +135 -0
  200. package/skills/paperclip-create-agent/references/agents/uxdesigner.md +115 -0
  201. package/skills/paperclip-create-agent/references/api-reference.md +110 -0
  202. package/skills/paperclip-create-agent/references/baseline-role-guide.md +168 -0
  203. package/skills/paperclip-create-agent/references/draft-review-checklist.md +95 -0
  204. package/skills/para-memory-files/SKILL.md +100 -0
  205. package/skills/para-memory-files/references/schemas.md +35 -0
  206. package/skills/slack/SKILL.md +65 -0
@@ -0,0 +1,140 @@
1
+ /**
2
+ * The fixed label a Test result shows when the probe runs on the local
3
+ * Paperclip host. The label is a constant, so a local target check never
4
+ * carries an environment ID, a config value, or a credential-derived string.
5
+ */
6
+ export const ADAPTER_TEST_HOST_TARGET_LABEL = "Paperclip host";
7
+ // The login hint may show a login URL. The URL must be a normalized https URL
8
+ // with an allowlisted Claude or Anthropic host and no query or fragment. A host
9
+ // matches when it equals a suffix or ends with a dot and the suffix.
10
+ const ALLOWED_LOGIN_URL_HOST_SUFFIXES = ["anthropic.com", "claude.ai"];
11
+ // A JavaScript error class name is a bounded identifier. The bound stops a very
12
+ // large or crafted class name from filling the log.
13
+ const MAX_ERROR_CLASS_NAME_CHARS = 64;
14
+ /**
15
+ * Read the class name of a thrown value for a safe probe diagnostic. The
16
+ * function returns the constructor name of an `Error`, or `null` for any other
17
+ * value. The name is a bounded identifier, not a copy of the error message, so
18
+ * it carries no untrusted probe text.
19
+ */
20
+ export function classifyThrownErrorClass(err) {
21
+ if (err instanceof Error)
22
+ return err.constructor?.name ?? "Error";
23
+ return null;
24
+ }
25
+ // Keep only identifier characters and bound the length. The result cannot carry
26
+ // untrusted probe text.
27
+ function sanitizeErrorClassName(name) {
28
+ if (typeof name !== "string")
29
+ return null;
30
+ const safe = name.replace(/[^A-Za-z0-9_$]/g, "").slice(0, MAX_ERROR_CLASS_NAME_CHARS);
31
+ return safe.length > 0 ? safe : null;
32
+ }
33
+ /**
34
+ * Send a sandbox probe or config materialization diagnostic to the server log.
35
+ *
36
+ * Three Test-lane call sites use this helper:
37
+ * - the Claude CLI Test lane (`test.ts`),
38
+ * - the Claude ACP Test lane (`acp.ts`),
39
+ * - the managed-config materialization step (`claude-config.ts`).
40
+ *
41
+ * Contract: no untrusted text reaches the log. The helper logs only the fixed
42
+ * context string, one allowlisted classification, and safe structured fields.
43
+ * The safe fields are the process exit code and a sanitized error class name.
44
+ * The helper never logs raw probe stdout, raw stderr, or a raw thrown-error
45
+ * message. A call site must never copy raw probe text into a Test-result check,
46
+ * because the user interface renders check text.
47
+ *
48
+ * @param context A short fixed description of the failed step. It carries no
49
+ * untrusted text.
50
+ * @param classification One allowlisted label that the call site derives from
51
+ * the probe state. It carries no untrusted text.
52
+ * @param fields Optional safe structured fields, such as the exit code.
53
+ */
54
+ export function logSandboxProbeDiagnostic(context, classification, fields) {
55
+ const detail = { classification };
56
+ if (typeof fields?.exitCode === "number" && Number.isFinite(fields.exitCode)) {
57
+ detail.exitCode = fields.exitCode;
58
+ }
59
+ const errorClass = sanitizeErrorClassName(fields?.errorClass);
60
+ if (errorClass)
61
+ detail.errorClass = errorClass;
62
+ console.warn(`[paperclip] ${context}`, detail);
63
+ }
64
+ /**
65
+ * Normalize an untrusted login URL for a Test-result hint.
66
+ *
67
+ * The extractor reads the URL from raw sandbox stdout or stderr, so the value is
68
+ * untrusted. The function accepts the URL only when every rule holds:
69
+ * - the protocol is `https`,
70
+ * - the host equals or ends with an allowlisted Claude or Anthropic host,
71
+ * - the URL has no user, password, or port,
72
+ * - the URL has no query and no fragment.
73
+ *
74
+ * The function returns the normalized URL string, or `null` when any rule
75
+ * fails. The caller shows a fixed `claude login` hint when the function returns
76
+ * `null`.
77
+ */
78
+ export function normalizeClaudeLoginUrl(raw) {
79
+ if (!raw)
80
+ return null;
81
+ let url;
82
+ try {
83
+ url = new URL(raw);
84
+ }
85
+ catch {
86
+ return null;
87
+ }
88
+ if (url.protocol !== "https:")
89
+ return null;
90
+ if (url.username || url.password || url.port)
91
+ return null;
92
+ if (url.search || url.hash)
93
+ return null;
94
+ const host = url.hostname.toLowerCase();
95
+ const allowed = ALLOWED_LOGIN_URL_HOST_SUFFIXES.some((suffix) => host === suffix || host.endsWith(`.${suffix}`));
96
+ if (!allowed)
97
+ return null;
98
+ return url.toString();
99
+ }
100
+ /**
101
+ * Build the fixed auth-required hint for a Test-result check. When the login URL
102
+ * normalizes to a safe value, the hint names it. Otherwise the hint tells the
103
+ * operator to run `claude login`.
104
+ */
105
+ export function buildClaudeLoginRequiredHint(loginUrl) {
106
+ const safeUrl = normalizeClaudeLoginUrl(loginUrl);
107
+ return safeUrl
108
+ ? `Run \`claude login\` and complete sign-in at ${safeUrl}, then retry.`
109
+ : "Run `claude login` in this environment, then retry the probe.";
110
+ }
111
+ /**
112
+ * Resolve the label a Test result shows for the probed target. A remote target
113
+ * uses the authorized environment name. A remote target with no name uses a
114
+ * fixed generic label. A local target uses the fixed host label. The function
115
+ * never returns an environment ID, a config value, or a credential-derived
116
+ * string.
117
+ */
118
+ export function resolveAdapterTestTargetLabel(input) {
119
+ if (!input.targetIsRemote)
120
+ return ADAPTER_TEST_HOST_TARGET_LABEL;
121
+ const name = typeof input.environmentName === "string" ? input.environmentName.trim() : "";
122
+ return name.length > 0 ? name : "the selected environment";
123
+ }
124
+ /**
125
+ * Build the target check every Test result carries, so the result names the
126
+ * target it probed. Both the Claude CLI Test lane and the Claude ACP Test lane
127
+ * use this builder. The check text carries only the authorized environment
128
+ * label or the fixed host label.
129
+ */
130
+ export function buildAdapterTestTargetCheck(input) {
131
+ const label = resolveAdapterTestTargetLabel(input);
132
+ return {
133
+ code: "claude_environment_target",
134
+ level: "info",
135
+ message: input.targetIsRemote
136
+ ? `Probing inside environment: ${label}`
137
+ : "Probing on the Paperclip host.",
138
+ };
139
+ }
140
+ //# sourceMappingURL=probe-diagnostics.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-diagnostics.js","sourceRoot":"","sources":["../../src/server/probe-diagnostics.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=probe-diagnostics.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-diagnostics.test.d.ts","sourceRoot":"","sources":["../../src/server/probe-diagnostics.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,114 @@
1
+ import { describe, expect, it, vi } from "vitest";
2
+ import { buildClaudeLoginRequiredHint, classifyThrownErrorClass, logSandboxProbeDiagnostic, normalizeClaudeLoginUrl, } from "./probe-diagnostics.js";
3
+ describe("normalizeClaudeLoginUrl", () => {
4
+ it("accepts an allowlisted https Claude host with no query or fragment", () => {
5
+ expect(normalizeClaudeLoginUrl("https://claude.ai/login")).toBe("https://claude.ai/login");
6
+ });
7
+ it("accepts an allowlisted Anthropic subdomain", () => {
8
+ expect(normalizeClaudeLoginUrl("https://console.anthropic.com/login")).toBe("https://console.anthropic.com/login");
9
+ });
10
+ it("rejects a URL with a query", () => {
11
+ expect(normalizeClaudeLoginUrl("https://claude.ai/login?token=secret")).toBeNull();
12
+ });
13
+ it("rejects a URL with a fragment", () => {
14
+ expect(normalizeClaudeLoginUrl("https://claude.ai/login#access_token=secret")).toBeNull();
15
+ });
16
+ it("rejects a non-https URL", () => {
17
+ expect(normalizeClaudeLoginUrl("http://claude.ai/login")).toBeNull();
18
+ });
19
+ it("rejects a non-allowlisted host", () => {
20
+ expect(normalizeClaudeLoginUrl("https://evil.example.com/claude-login")).toBeNull();
21
+ });
22
+ it("rejects a look-alike host that only ends with the brand word", () => {
23
+ expect(normalizeClaudeLoginUrl("https://claude.ai.evil.com/login")).toBeNull();
24
+ expect(normalizeClaudeLoginUrl("https://notclaude.ai/login")).toBeNull();
25
+ });
26
+ it("rejects a URL that embeds credentials or a port", () => {
27
+ expect(normalizeClaudeLoginUrl("https://user:pass@claude.ai/login")).toBeNull();
28
+ expect(normalizeClaudeLoginUrl("https://claude.ai:8443/login")).toBeNull();
29
+ });
30
+ it("returns null for empty or malformed input", () => {
31
+ expect(normalizeClaudeLoginUrl(null)).toBeNull();
32
+ expect(normalizeClaudeLoginUrl(undefined)).toBeNull();
33
+ expect(normalizeClaudeLoginUrl("not a url")).toBeNull();
34
+ });
35
+ });
36
+ describe("buildClaudeLoginRequiredHint", () => {
37
+ it("names a safe login URL in the hint", () => {
38
+ expect(buildClaudeLoginRequiredHint("https://claude.ai/login")).toBe("Run `claude login` and complete sign-in at https://claude.ai/login, then retry.");
39
+ });
40
+ it("falls back to the fixed hint for an unsafe URL", () => {
41
+ expect(buildClaudeLoginRequiredHint("https://evil.example.com/claude-login?leak=secret")).toBe("Run `claude login` in this environment, then retry the probe.");
42
+ });
43
+ it("falls back to the fixed hint for a null URL", () => {
44
+ expect(buildClaudeLoginRequiredHint(null)).toBe("Run `claude login` in this environment, then retry the probe.");
45
+ });
46
+ });
47
+ describe("classifyThrownErrorClass", () => {
48
+ it("returns the constructor name for an Error", () => {
49
+ expect(classifyThrownErrorClass(new TypeError("boom"))).toBe("TypeError");
50
+ expect(classifyThrownErrorClass(new Error("boom"))).toBe("Error");
51
+ });
52
+ it("returns null for a non-Error value", () => {
53
+ expect(classifyThrownErrorClass("a raw secret string")).toBeNull();
54
+ expect(classifyThrownErrorClass(null)).toBeNull();
55
+ expect(classifyThrownErrorClass({ message: "opaque" })).toBeNull();
56
+ });
57
+ });
58
+ describe("logSandboxProbeDiagnostic", () => {
59
+ it("logs only the fixed context and the allowlisted classification", () => {
60
+ const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => { });
61
+ logSandboxProbeDiagnostic("probe failed", "auth_required");
62
+ expect(warnSpy).toHaveBeenCalledTimes(1);
63
+ expect(warnSpy).toHaveBeenCalledWith("[paperclip] probe failed", {
64
+ classification: "auth_required",
65
+ });
66
+ warnSpy.mockRestore();
67
+ });
68
+ it("adds a finite exit code as a structured field", () => {
69
+ const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => { });
70
+ logSandboxProbeDiagnostic("probe failed", "nonzero_exit", { exitCode: 3 });
71
+ expect(warnSpy).toHaveBeenCalledWith("[paperclip] probe failed", {
72
+ classification: "nonzero_exit",
73
+ exitCode: 3,
74
+ });
75
+ warnSpy.mockRestore();
76
+ });
77
+ it("drops a null or non-finite exit code", () => {
78
+ const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => { });
79
+ logSandboxProbeDiagnostic("probe failed", "nonzero_exit", { exitCode: null });
80
+ logSandboxProbeDiagnostic("probe failed", "nonzero_exit", { exitCode: Number.NaN });
81
+ for (const call of warnSpy.mock.calls) {
82
+ expect(call[1]).toEqual({ classification: "nonzero_exit" });
83
+ }
84
+ warnSpy.mockRestore();
85
+ });
86
+ it("sanitizes the error class to an identifier and bounds its length", () => {
87
+ const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => { });
88
+ // A crafted error class name that carries an opaque marker and a proxy URL.
89
+ // The sanitizer must strip every non-identifier character and bound the
90
+ // length, so no structured secret shape reaches the log.
91
+ logSandboxProbeDiagnostic("probe failed", "spawn_error", {
92
+ errorClass: `MARKER-LEAK http://user:pass@proxy.internal:8080/path?t=${"x".repeat(200)}`,
93
+ });
94
+ expect(warnSpy).toHaveBeenCalledTimes(1);
95
+ const detail = warnSpy.mock.calls[0][1];
96
+ expect(detail.errorClass).toMatch(/^[A-Za-z0-9_$]+$/);
97
+ expect(detail.errorClass.length).toBeLessThanOrEqual(64);
98
+ // The separators and the proxy structure do not survive.
99
+ expect(detail.errorClass).not.toContain("-");
100
+ expect(detail.errorClass).not.toContain(":");
101
+ expect(detail.errorClass).not.toContain("/");
102
+ warnSpy.mockRestore();
103
+ });
104
+ it("drops an empty or non-string error class", () => {
105
+ const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => { });
106
+ logSandboxProbeDiagnostic("probe failed", "spawn_error", { errorClass: null });
107
+ logSandboxProbeDiagnostic("probe failed", "spawn_error", { errorClass: "***" });
108
+ for (const call of warnSpy.mock.calls) {
109
+ expect(call[1]).toEqual({ classification: "spawn_error" });
110
+ }
111
+ warnSpy.mockRestore();
112
+ });
113
+ });
114
+ //# sourceMappingURL=probe-diagnostics.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-diagnostics.test.js","sourceRoot":"","sources":["../../src/server/probe-diagnostics.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,42 @@
1
+ export interface LocalProbeEnvironment {
2
+ /**
3
+ * The trusted absolute path to the resolved `claude` executable, or `null`
4
+ * when the trusted server PATH holds no `claude`. The caller must not run a
5
+ * local probe when this is `null`; it reports a probe-unavailable check
6
+ * instead.
7
+ */
8
+ command: string | null;
9
+ /**
10
+ * The child environment for the local probe. It holds only allowlisted
11
+ * caller values plus proxy values from the trusted input. It never holds a
12
+ * caller-supplied proxy key, a loader variable, a PATH override, or a Windows
13
+ * interpreter variable.
14
+ */
15
+ env: Record<string, string>;
16
+ }
17
+ /**
18
+ * Build the child environment and executable for a local Claude adapter-test
19
+ * hello probe. Both the ACP Test lane and the Claude CLI Test lane use this
20
+ * builder, so the two lanes probe the host the same safe way.
21
+ *
22
+ * The builder denies by default. It never merges the arbitrary caller env into
23
+ * a host base. It reads two separate inputs:
24
+ * - `callerEnv`: the untrusted adapter-config env from the Test request. The
25
+ * builder takes only allowlisted Claude, auth, and Bedrock keys from it. It
26
+ * discards every proxy key and every Windows interpreter key, in any case.
27
+ * - `trustedEnv`: the trusted server-resolved env (the server launch config
28
+ * and the authorized environment's server-resolved env). The builder takes
29
+ * proxy keys only from this input.
30
+ *
31
+ * The builder resolves `claude` to a trusted absolute executable with the
32
+ * trusted server PATH, before it reads any caller value. It ignores a caller
33
+ * `command` path.
34
+ *
35
+ * The builder never logs, returns, or reflects a proxy value in a check.
36
+ */
37
+ export declare function buildLocalAdapterTestProbeEnv(input: {
38
+ callerEnv: Record<string, string>;
39
+ trustedEnv?: NodeJS.ProcessEnv;
40
+ commandName?: string;
41
+ }): Promise<LocalProbeEnvironment>;
42
+ //# sourceMappingURL=probe-env.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-env.d.ts","sourceRoot":"","sources":["../../src/server/probe-env.ts"],"names":[],"mappings":"AA+CA,MAAM,WAAW,qBAAqB;IACpC;;;;;OAKG;IACH,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB;;;;;OAKG;IACH,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAC7B;AA4DD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAsB,6BAA6B,CAAC,KAAK,EAAE;IACzD,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAClC,UAAU,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IAC/B,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,GAAG,OAAO,CAAC,qBAAqB,CAAC,CAwCjC"}
@@ -0,0 +1,149 @@
1
+ import { access } from "node:fs/promises";
2
+ import { constants as fsConstants } from "node:fs";
3
+ import path from "node:path";
4
+ /**
5
+ * The environment variable names that a local Claude adapter-test probe may
6
+ * take from the untrusted adapter configuration. The builder denies every
7
+ * other key by default. The list holds the documented Claude, Anthropic auth,
8
+ * and AWS Bedrock variables that the probe needs to reach the real credential
9
+ * the agent run uses.
10
+ */
11
+ const LOCAL_PROBE_ALLOWED_CALLER_ENV_KEYS = [
12
+ // Claude and Anthropic subscription and API auth.
13
+ "ANTHROPIC_API_KEY",
14
+ "ANTHROPIC_AUTH_TOKEN",
15
+ "CLAUDE_CODE_OAUTH_TOKEN",
16
+ "ANTHROPIC_BASE_URL",
17
+ "ANTHROPIC_MODEL",
18
+ "ANTHROPIC_SMALL_FAST_MODEL",
19
+ "CLAUDE_CONFIG_DIR",
20
+ // AWS Bedrock inference.
21
+ "CLAUDE_CODE_USE_BEDROCK",
22
+ "ANTHROPIC_BEDROCK_BASE_URL",
23
+ "AWS_BEARER_TOKEN_BEDROCK",
24
+ "AWS_ACCESS_KEY_ID",
25
+ "AWS_SECRET_ACCESS_KEY",
26
+ "AWS_SESSION_TOKEN",
27
+ "AWS_PROFILE",
28
+ "AWS_REGION",
29
+ "AWS_DEFAULT_REGION",
30
+ ];
31
+ /**
32
+ * The proxy variable names the probe may forward. The builder reads these only
33
+ * from the trusted server-resolved input. It never reads a proxy key from the
34
+ * untrusted caller input, and it never logs, returns, or reflects a proxy
35
+ * value.
36
+ */
37
+ const PROXY_ENV_KEYS = ["HTTP_PROXY", "HTTPS_PROXY", "NO_PROXY"];
38
+ /**
39
+ * Windows interpreter-selection variables. The builder never takes these from
40
+ * any input. The child-process launcher derives the interpreter from trusted
41
+ * server state instead, so a caller value must never reach the child env.
42
+ */
43
+ const WINDOWS_INTERPRETER_ENV_KEYS = new Set(["SYSTEMROOT", "WINDIR", "COMSPEC"]);
44
+ function isNonEmptyString(value) {
45
+ return typeof value === "string" && value.trim().length > 0;
46
+ }
47
+ function readCaseInsensitive(source, key) {
48
+ const direct = source[key];
49
+ if (typeof direct === "string")
50
+ return direct;
51
+ const upper = key.toUpperCase();
52
+ for (const [candidateKey, candidateValue] of Object.entries(source)) {
53
+ if (candidateKey.toUpperCase() === upper && typeof candidateValue === "string") {
54
+ return candidateValue;
55
+ }
56
+ }
57
+ return undefined;
58
+ }
59
+ /**
60
+ * Resolve a command name to a trusted absolute executable. The function reads
61
+ * the PATH and PATHEXT from the trusted server env only. It never reads a
62
+ * caller value, so a hostile caller PATH cannot select the executable. The
63
+ * function ignores a command that contains a path separator; a local probe
64
+ * must not run a caller-supplied executable path.
65
+ */
66
+ async function resolveTrustedExecutable(commandName, trustedEnv) {
67
+ if (commandName.includes("/") || commandName.includes("\\")) {
68
+ return null;
69
+ }
70
+ const pathValue = trustedEnv.PATH ?? trustedEnv.Path ?? "";
71
+ const delimiter = process.platform === "win32" ? ";" : ":";
72
+ const dirs = pathValue.split(delimiter).filter(Boolean);
73
+ const exts = process.platform === "win32"
74
+ ? (trustedEnv.PATHEXT ?? ".EXE;.CMD;.BAT;.COM").split(";").filter(Boolean)
75
+ : [""];
76
+ const mode = process.platform === "win32" ? fsConstants.F_OK : fsConstants.X_OK;
77
+ for (const dir of dirs) {
78
+ const candidates = process.platform === "win32"
79
+ ? exts.map((ext) => path.join(dir, `${commandName}${ext}`))
80
+ : [path.join(dir, commandName)];
81
+ for (const candidate of candidates) {
82
+ try {
83
+ await access(candidate, mode);
84
+ return candidate;
85
+ }
86
+ catch {
87
+ // Try the next candidate.
88
+ }
89
+ }
90
+ }
91
+ return null;
92
+ }
93
+ /**
94
+ * Build the child environment and executable for a local Claude adapter-test
95
+ * hello probe. Both the ACP Test lane and the Claude CLI Test lane use this
96
+ * builder, so the two lanes probe the host the same safe way.
97
+ *
98
+ * The builder denies by default. It never merges the arbitrary caller env into
99
+ * a host base. It reads two separate inputs:
100
+ * - `callerEnv`: the untrusted adapter-config env from the Test request. The
101
+ * builder takes only allowlisted Claude, auth, and Bedrock keys from it. It
102
+ * discards every proxy key and every Windows interpreter key, in any case.
103
+ * - `trustedEnv`: the trusted server-resolved env (the server launch config
104
+ * and the authorized environment's server-resolved env). The builder takes
105
+ * proxy keys only from this input.
106
+ *
107
+ * The builder resolves `claude` to a trusted absolute executable with the
108
+ * trusted server PATH, before it reads any caller value. It ignores a caller
109
+ * `command` path.
110
+ *
111
+ * The builder never logs, returns, or reflects a proxy value in a check.
112
+ */
113
+ export async function buildLocalAdapterTestProbeEnv(input) {
114
+ const trustedEnv = input.trustedEnv ?? process.env;
115
+ const commandName = input.commandName ?? "claude";
116
+ const command = await resolveTrustedExecutable(commandName, trustedEnv);
117
+ const env = {};
118
+ // Allowlisted caller values. Read each allowed key by name so no unexpected
119
+ // caller key can enter the child env. Proxy and Windows interpreter keys are
120
+ // never in the allowlist, so a caller cannot pass them here.
121
+ for (const key of LOCAL_PROBE_ALLOWED_CALLER_ENV_KEYS) {
122
+ const value = readCaseInsensitive(input.callerEnv, key);
123
+ if (isNonEmptyString(value)) {
124
+ env[key] = value;
125
+ }
126
+ }
127
+ // Proxy values come from the trusted input only. A caller-supplied proxy key
128
+ // in `callerEnv` is never read, so it cannot reach the child.
129
+ for (const key of PROXY_ENV_KEYS) {
130
+ const upperValue = trustedEnv[key];
131
+ if (isNonEmptyString(upperValue)) {
132
+ env[key] = upperValue;
133
+ }
134
+ const lowerKey = key.toLowerCase();
135
+ const lowerValue = trustedEnv[lowerKey];
136
+ if (isNonEmptyString(lowerValue)) {
137
+ env[lowerKey] = lowerValue;
138
+ }
139
+ }
140
+ // Defense in depth: strip any Windows interpreter key that a future allowlist
141
+ // edit might introduce, in any case.
142
+ for (const key of Object.keys(env)) {
143
+ if (WINDOWS_INTERPRETER_ENV_KEYS.has(key.toUpperCase())) {
144
+ delete env[key];
145
+ }
146
+ }
147
+ return { command, env };
148
+ }
149
+ //# sourceMappingURL=probe-env.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-env.js","sourceRoot":"","sources":["../../src/server/probe-env.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=probe-env.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-env.test.d.ts","sourceRoot":"","sources":["../../src/server/probe-env.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,135 @@
1
+ import { afterEach, describe, expect, it } from "vitest";
2
+ import { chmod, mkdtemp, rm, writeFile } from "node:fs/promises";
3
+ import os from "node:os";
4
+ import path from "node:path";
5
+ import { buildLocalAdapterTestProbeEnv } from "./probe-env.js";
6
+ const tempDirs = [];
7
+ async function makeTrustedPathWithClaude() {
8
+ const dir = await mkdtemp(path.join(os.tmpdir(), "paperclip-probe-env-"));
9
+ tempDirs.push(dir);
10
+ const claudePath = path.join(dir, "claude");
11
+ await writeFile(claudePath, "#!/bin/sh\nexit 0\n");
12
+ await chmod(claudePath, 0o755);
13
+ return { dir, claudePath };
14
+ }
15
+ afterEach(async () => {
16
+ while (tempDirs.length > 0) {
17
+ const dir = tempDirs.pop();
18
+ if (dir)
19
+ await rm(dir, { recursive: true, force: true }).catch(() => undefined);
20
+ }
21
+ });
22
+ describe("buildLocalAdapterTestProbeEnv", () => {
23
+ it("resolves claude from the trusted PATH and ignores the caller PATH", async () => {
24
+ const { dir, claudePath } = await makeTrustedPathWithClaude();
25
+ const built = await buildLocalAdapterTestProbeEnv({
26
+ callerEnv: { PATH: "/hostile/bin", Path: "/hostile/bin", command: "/tmp/evil/claude" },
27
+ trustedEnv: { PATH: dir },
28
+ });
29
+ expect(built.command).toBe(claudePath);
30
+ expect(built.env.PATH).toBeUndefined();
31
+ expect(built.env.Path).toBeUndefined();
32
+ });
33
+ it("returns a null command when the trusted PATH holds no claude", async () => {
34
+ const dir = await mkdtemp(path.join(os.tmpdir(), "paperclip-probe-env-empty-"));
35
+ tempDirs.push(dir);
36
+ const built = await buildLocalAdapterTestProbeEnv({
37
+ callerEnv: {},
38
+ trustedEnv: { PATH: dir },
39
+ });
40
+ expect(built.command).toBeNull();
41
+ });
42
+ it("keeps the allowlisted Claude, auth, and Bedrock values", async () => {
43
+ const { dir } = await makeTrustedPathWithClaude();
44
+ const built = await buildLocalAdapterTestProbeEnv({
45
+ callerEnv: {
46
+ ANTHROPIC_API_KEY: "api-key-value",
47
+ CLAUDE_CODE_OAUTH_TOKEN: "oauth-token-value",
48
+ CLAUDE_CODE_USE_BEDROCK: "1",
49
+ ANTHROPIC_BEDROCK_BASE_URL: "https://bedrock.example",
50
+ AWS_ACCESS_KEY_ID: "aws-key",
51
+ AWS_SECRET_ACCESS_KEY: "aws-secret",
52
+ AWS_REGION: "us-east-1",
53
+ CLAUDE_CONFIG_DIR: "/managed/config",
54
+ },
55
+ trustedEnv: { PATH: dir },
56
+ });
57
+ expect(built.env.ANTHROPIC_API_KEY).toBe("api-key-value");
58
+ expect(built.env.CLAUDE_CODE_OAUTH_TOKEN).toBe("oauth-token-value");
59
+ expect(built.env.CLAUDE_CODE_USE_BEDROCK).toBe("1");
60
+ expect(built.env.ANTHROPIC_BEDROCK_BASE_URL).toBe("https://bedrock.example");
61
+ expect(built.env.AWS_ACCESS_KEY_ID).toBe("aws-key");
62
+ expect(built.env.AWS_SECRET_ACCESS_KEY).toBe("aws-secret");
63
+ expect(built.env.AWS_REGION).toBe("us-east-1");
64
+ expect(built.env.CLAUDE_CONFIG_DIR).toBe("/managed/config");
65
+ });
66
+ it("drops hostile loader, PATH, shell-startup, and Windows interpreter keys", async () => {
67
+ const { dir } = await makeTrustedPathWithClaude();
68
+ const built = await buildLocalAdapterTestProbeEnv({
69
+ callerEnv: {
70
+ PATH: "/hostile/bin",
71
+ Path: "/hostile/bin",
72
+ PATHEXT: ".EVIL",
73
+ LD_PRELOAD: "/hostile/lib/evil.so",
74
+ LD_LIBRARY_PATH: "/hostile/lib",
75
+ DYLD_INSERT_LIBRARIES: "/hostile/lib/evil.dylib",
76
+ DYLD_LIBRARY_PATH: "/hostile/lib",
77
+ NODE_OPTIONS: "--require /hostile/evil.js",
78
+ ENV: "/hostile/profile",
79
+ BASH_ENV: "/hostile/bashrc",
80
+ SystemRoot: "C:\\hostile",
81
+ systemroot: "C:\\hostile",
82
+ WINDIR: "C:\\hostile",
83
+ windir: "C:\\hostile",
84
+ ComSpec: "C:\\hostile\\evil.exe",
85
+ comspec: "C:\\hostile\\evil.exe",
86
+ },
87
+ trustedEnv: { PATH: dir },
88
+ });
89
+ for (const key of Object.keys(built.env)) {
90
+ expect(key.toUpperCase()).not.toBe("PATH");
91
+ expect(key.toUpperCase()).not.toBe("PATHEXT");
92
+ expect(key.toUpperCase()).not.toBe("LD_PRELOAD");
93
+ expect(key.toUpperCase()).not.toBe("LD_LIBRARY_PATH");
94
+ expect(key.toUpperCase()).not.toBe("DYLD_INSERT_LIBRARIES");
95
+ expect(key.toUpperCase()).not.toBe("DYLD_LIBRARY_PATH");
96
+ expect(key.toUpperCase()).not.toBe("NODE_OPTIONS");
97
+ expect(key.toUpperCase()).not.toBe("ENV");
98
+ expect(key.toUpperCase()).not.toBe("BASH_ENV");
99
+ expect(key.toUpperCase()).not.toBe("SYSTEMROOT");
100
+ expect(key.toUpperCase()).not.toBe("WINDIR");
101
+ expect(key.toUpperCase()).not.toBe("COMSPEC");
102
+ }
103
+ });
104
+ it("takes proxy values only from the trusted env, never from the caller", async () => {
105
+ const { dir } = await makeTrustedPathWithClaude();
106
+ const built = await buildLocalAdapterTestProbeEnv({
107
+ callerEnv: {
108
+ HTTP_PROXY: "http://caller-proxy:8080",
109
+ HTTPS_PROXY: "http://caller-proxy:8443",
110
+ http_proxy: "http://caller-proxy-lower:8080",
111
+ NO_PROXY: "caller.example",
112
+ },
113
+ trustedEnv: { PATH: dir, HTTPS_PROXY: "http://trusted-proxy:8443" },
114
+ });
115
+ // The trusted proxy reaches the child; the caller proxy does not.
116
+ expect(built.env.HTTPS_PROXY).toBe("http://trusted-proxy:8443");
117
+ expect(built.env.HTTP_PROXY).toBeUndefined();
118
+ expect(built.env.http_proxy).toBeUndefined();
119
+ expect(built.env.NO_PROXY).toBeUndefined();
120
+ // No env value carries the caller proxy host.
121
+ const serialized = JSON.stringify(built.env);
122
+ expect(serialized).not.toContain("caller-proxy");
123
+ });
124
+ it("forwards no proxy variable when the trusted env has none", async () => {
125
+ const { dir } = await makeTrustedPathWithClaude();
126
+ const built = await buildLocalAdapterTestProbeEnv({
127
+ callerEnv: { HTTP_PROXY: "http://caller-proxy:8080", https_proxy: "http://caller:8443" },
128
+ trustedEnv: { PATH: dir },
129
+ });
130
+ for (const key of Object.keys(built.env)) {
131
+ expect(key.toUpperCase()).not.toContain("PROXY");
132
+ }
133
+ });
134
+ });
135
+ //# sourceMappingURL=probe-env.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"probe-env.test.js","sourceRoot":"","sources":["../../src/server/probe-env.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=probe-redaction.test.d.ts.map