@reclaimprotocol/agent 0.1.34 → 0.1.36

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 (49) hide show
  1. package/README.md +3 -3
  2. package/lib/mcp/api/operations.gen.js +340 -150
  3. package/lib/mcp/instructions.js +3 -3
  4. package/lib/mcp/start.js +8 -7
  5. package/lib/mcp/tools/agent/build.js +2 -0
  6. package/lib/mcp/tools/agent/check-attestor.d.ts +5 -0
  7. package/lib/mcp/tools/agent/check-attestor.js +37 -0
  8. package/lib/mcp/tools/agent/live-view.js +42 -18
  9. package/lib/mcp/tools/agent/proof.d.ts +12 -0
  10. package/lib/mcp/tools/agent/proof.js +32 -0
  11. package/lib/mcp/tools/agent/shared.d.ts +2 -1
  12. package/lib/mcp/tools/agent/shared.js +28 -24
  13. package/lib/mcp/tools/agent/start-integration.js +5 -4
  14. package/lib/mcp/tools/verification/build.d.ts +3 -1
  15. package/lib/mcp/tools/verification/build.js +10 -2
  16. package/lib/mcp/tools/verification/callback-listener.d.ts +51 -0
  17. package/lib/mcp/tools/verification/callback-listener.js +163 -0
  18. package/lib/mcp/tools/verification/index.d.ts +2 -0
  19. package/lib/mcp/tools/verification/index.js +2 -0
  20. package/lib/mcp/tools/verification/proxy-callback-events.d.ts +77 -0
  21. package/lib/mcp/tools/verification/proxy-callback-events.js +383 -0
  22. package/lib/mcp/tools/verification/read-callback-events.d.ts +3 -0
  23. package/lib/mcp/tools/verification/read-callback-events.js +135 -0
  24. package/lib/mcp/tools/verification/result.d.ts +6 -0
  25. package/lib/mcp/tools/verification/result.js +1 -1
  26. package/lib/proof/check-attestor.d.ts +67 -0
  27. package/lib/proof/check-attestor.js +156 -0
  28. package/package.json +2 -2
  29. package/skill/SKILL.builder.md +7 -1
  30. package/skill/SKILL.common.md +21 -9
  31. package/skill/builder-mode.md +25 -12
  32. package/skill/start-integration.md +37 -11
  33. package/skill/verification-client-integration.md +81 -18
  34. package/src/mcp/api/operations.gen.ts +344 -150
  35. package/src/mcp/instructions.ts +3 -3
  36. package/src/mcp/start.ts +9 -7
  37. package/src/mcp/tools/agent/build.ts +2 -0
  38. package/src/mcp/tools/agent/check-attestor.ts +49 -0
  39. package/src/mcp/tools/agent/live-view.ts +42 -18
  40. package/src/mcp/tools/agent/proof.ts +55 -0
  41. package/src/mcp/tools/agent/shared.ts +33 -23
  42. package/src/mcp/tools/agent/start-integration.ts +5 -4
  43. package/src/mcp/tools/verification/build.ts +10 -2
  44. package/src/mcp/tools/verification/callback-listener.ts +203 -0
  45. package/src/mcp/tools/verification/index.ts +2 -0
  46. package/src/mcp/tools/verification/proxy-callback-events.ts +484 -0
  47. package/src/mcp/tools/verification/read-callback-events.ts +160 -0
  48. package/src/mcp/tools/verification/result.ts +1 -1
  49. package/src/proof/check-attestor.ts +209 -0
@@ -21,12 +21,16 @@ server), or migrate to the session flow below. When migrating, remove
21
21
  1. `get_devtools_mode` confirms Builder mode. `get_me` or `authenticate` signs
22
22
  in the developer. Find the organization with `list_orgs`; call `create_org`
23
23
  only when they want a new one.
24
- 2. Register a callback URL owned by the app's backend with
25
- `create_org_callback_subscription`. Include terminal success, rejection,
26
- error, cancellation, and expiry events. If the app needs encrypted results,
27
- register its public key with `set_org_keypair`; keep the private key only in
28
- the backend. `set_org_keypair` refuses to replace an existing key unless you
29
- pass `replace: true`; pass it only when the developer asks.
24
+ 2. Receive callbacks. Local development: call
25
+ `proxy_callback_events({ port, path })` to forward the org's events to the
26
+ app's callback route on localhost; no public URL. Deployed app (required for
27
+ production): register a
28
+ public callback URL with `create_org_callback_subscription`, including
29
+ all five session-ending events. If the
30
+ app needs encrypted results, register its public key with `set_org_keypair`;
31
+ keep the private key only in the backend. `set_org_keypair` refuses to
32
+ replace an existing key unless you pass `replace: true`; pass it only when
33
+ the developer asks.
30
34
  3. Org key: reuse the `RECLAIM_ORG_SECRET` the app already has. Otherwise an
31
35
  organization owner calls `issue_org_token`. It writes the key to the
32
36
  project's env file (default `.env`, variable `RECLAIM_ORG_SECRET`) and
@@ -43,12 +47,22 @@ server), or migrate to the session flow below. When migrating, remove
43
47
  is not proof of success. Use `@reclaimprotocol/client`
44
48
  (`ReclaimVerification.create({ orgSecret })`, `sessions.create`) only when
45
49
  the developer asks for it.
46
- 5. Add a backend callback endpoint. Persist each delivery idempotently and load
50
+ 5. Add a backend callback route. Persist each delivery idempotently and load
47
51
  the expected session ID and org ID from app storage. To verify the result on
48
- your callback, install `@reclaimprotocol/client` in the backend and call
52
+ your callback route, install `@reclaimprotocol/client` in the backend and call
49
53
  `reclaim.results.receive(body, { reclaimSessionId, expectedAud,
50
54
  orgEthPrivateKey })`. Use the verified proof data to update app state.
51
- Handle callback retries and terminal failure outcomes.
55
+ Store every failure on the verification session record: failure events, and
56
+ a thrown `ResultVerificationError` (`error.reason` and each
57
+ `error.outcome.proofs[].reason`). Respond `error.retryable ? 503 : 200`.
58
+ A result that failed verification gets 2xx: retrying can't fix it, and an
59
+ unacknowledged delivery holds back that session's later events. Respond 5xx
60
+ for any other temporary problem too, such as a database outage.
61
+ Add a status route that returns the stored status, data points, and failure
62
+ reason. While the app has no result, it also reads
63
+ `GET /verifications/sessions/{sessionId}`, so a session Builder has ended
64
+ never stays pending in the app. Render the frontend per
65
+ [UI states](#ui-states).
52
66
  6. Exercise one session through the selected registered Verification Client,
53
67
  inspect its Builder events, and test the app's success and failure paths.
54
68
  Omit `verificationClientUrl` to use the Portal, or select another client
@@ -75,10 +89,12 @@ Use the API base URL the developer's Builder runs at (production:
75
89
  `https://build.reclaimprotocol.org`). Every call authenticates with
76
90
  `authorization: Bearer $RECLAIM_ORG_SECRET`.
77
91
 
78
- Subscribe a callback once (or use `create_org_callback_subscription`). Session
79
- creation returns 409 while the org has none, and a result is only delivered to
92
+ Deployed apps subscribe a callback once (or use
93
+ `create_org_callback_subscription`); local development uses
94
+ `proxy_callback_events` instead. Session creation returns 409 while the org has
95
+ no subscription, and a result is only delivered to
80
96
  subscriptions that include the event the session ends with, so subscribe to all
81
- five:
97
+ five session-ending events:
82
98
 
83
99
  ```bash
84
100
  curl -X POST https://build.reclaimprotocol.org/verifications/callback-subscriptions \
@@ -119,16 +135,37 @@ Receive and verify the result on the callback route. This is the one place the
119
135
  client package is needed:
120
136
 
121
137
  ```js
122
- import { ReclaimVerification } from '@reclaimprotocol/client'
138
+ import { ReclaimVerification, ResultVerificationError } from '@reclaimprotocol/client'
123
139
 
124
140
  const reclaim = ReclaimVerification.create({
125
141
  orgSecret: process.env.RECLAIM_ORG_SECRET,
126
142
  })
127
143
 
128
144
  app.post('/reclaim/callback', async(req, res) => {
129
- const outcome = await reclaim.results.receive(req.body, {
130
- reclaimSessionId: sessionId, // the id you stored
131
- })
145
+ let outcome
146
+ try {
147
+ outcome = await reclaim.results.receive(req.body, {
148
+ reclaimSessionId: sessionId, // the id you stored
149
+ })
150
+ } catch(error) {
151
+ if(!(error instanceof ResultVerificationError)) {
152
+ throw error
153
+ }
154
+
155
+ if(error.retryable) {
156
+ return res.sendStatus(503) // temporary: Builder retries the delivery
157
+ }
158
+
159
+ // Retrying can't fix a result that failed verification. Store the failure
160
+ // where the status route returns it, then acknowledge the delivery.
161
+ const proofReasons = (error.outcome.proofs ?? [])
162
+ .filter((proof) => !proof.proofValid)
163
+ .map((proof) => proof.reason)
164
+ console.warn('result failed verification', error.reason, proofReasons)
165
+ await markSessionFailed(sessionId, error.reason) // your app's storage
166
+ return res.sendStatus(200)
167
+ }
168
+
132
169
  if(outcome.kind === 'result') {
133
170
  console.log(outcome.result.payload) // verified
134
171
  }
@@ -137,8 +174,34 @@ app.post('/reclaim/callback', async(req, res) => {
137
174
  })
138
175
  ```
139
176
 
140
- Check or investigate a session, from the backend (optional, e.g. a status
141
- endpoint the frontend polls) or by hand with `curl`. All take the org key:
177
+ ### UI states
178
+
179
+ Apply these rules when you write the frontend. Test each state, including one
180
+ failure.
181
+
182
+ | State | Render |
183
+ | --- | --- |
184
+ | Idle | The **Verify** button. |
185
+ | Waiting in the other tab | The current step ("Finish verifying in the new tab") and a way to reopen `verificationUrl`. After about 30 seconds, say what is happening and offer **Cancel** or **Try again**. |
186
+ | Verifying | "Checking your result". |
187
+ | Verified | The requested data points. |
188
+ | Failed | A plain-language reason and what to do next, near the **Verify** button, with **Try again**. |
189
+ | Expired or cancelled | Say which, with **Try again**. |
190
+
191
+ - Show the current step, never an indefinite spinner (Nielsen heuristic 1,
192
+ visibility of system status).
193
+ - Write errors in plain language that says what happened and what to do next,
194
+ visible next to the action, with a recovery action (Nielsen Norman Group
195
+ error-message guidelines).
196
+ - Send reason codes (`error.reason`, proof `reason`) to logs or an expandable
197
+ **Details** section, not the headline.
198
+ - Announce changes: `role="status"` (or `aria-live="polite"`) for progress,
199
+ `role="alert"` for failures (WCAG 2.2 SC 4.1.3).
200
+ - Pair color with text or an icon (WCAG 2.2 SC 1.4.1).
201
+ - Stop the waiting state when the status route reports a terminal status.
202
+
203
+ Check or investigate a session from the status route or by hand with `curl`.
204
+ All routes take the org key:
142
205
 
143
206
  | Route | Use |
144
207
  | --- | --- |