Independent Forgejo repo maps every verae.* address, endpoint I/O, job monitor loop, and remaining billing/archive wiring.
4.7 KiB
Zapier → Verae API → Zapier
How a timestamp job is submitted, watched, and returned. Lab today: MOCK_VERAE=true. Live path is the same HTTP contract with MOCK_VERAE=false.
Rule
Zapier cloud --HTTPS only--> zap.zapier.georgelambert.org (access-zapier)
|
v HTTPS
middleware :3100 /zapier/v1
|
+---------------+----------------+
| HTTPS | NATS (private cluster)
v v
api.veraetime.net jobs.watch → poller
POST /api/timestamp GET /api/status/{jobId}
GET /api/status/{jobId} |
POST /api/verify v
jobs.events
|
+--------------------+--------------------+
| wait subscriber | webhook-deliver
v v
HTTP response to Zap POST hooks.zapier.com
Zapier never has NATS_URL. Verae never has NATS_URL.
1. Submit (async create)
- Zap action Create Timestamp (or curl)
POST https://zap.zapier.georgelambert.org/zapier/v1/timestampwith portal API keyzmw_…(not a Verae JWT). - access-zapier / edge meters (designed:
verae.billing.usage.recorded) and forwards to middleware. - Middleware
checkEntitlement(local plan limits today). veraeClient.createTimestamp:- Mock: in-process job, fake
jobId. - Live:
POST https://api.veraetime.net/api/timestampwith JWT → 202{ jobId }.
- Mock: in-process job, fake
- Splitter (in-process): hash vs attachments; optional
verae.archive.put(bytes never go to chain). enqueueWatch→ JetStreamverae.zapier.jobs.watch.- HTTP 202
{ jobId, sha256, existing }back to Zapier immediately.
Same SHA-256 is idempotent (existing: true).
2. Monitor (job poller)
The poller is in the middleware Node process when NATS_ENABLED=true (startJobPollerWorker). Fleet does not spawn a second copy (job-poller.enabled: false).
- Durable consumer
job-polleronZAPIER_JOBS/verae.zapier.jobs.watch. - Resolve
tokenRef→ tenant Verae password →POSTlogin → JWT (stays in middleware). GET /api/status/{jobId}(mock or live).pending→nakafterintervalMs(retry).completed→ publishjobs.events{ event: timestamp.completed, status, jobId, tenantId, traceId }.failed→timestamp.failed. Too many attempts →timestamp.timeout.ackthe watch message.
Live OpenAPI: poll until completed / failed. Hash lookup is 501 on live (lookupHash). Map certificate, timestamp, blockIndex, sha256 into the receipt Zap samples expect.
3. Wait (sync Zap step)
Create Timestamp and Wait → POST /zapier/v1/timestamp/wait.
- Same as submit (watch is already on NATS).
waitForJobEvent(jobId, WAIT_TIMEOUT_MS)subscribes toverae.zapier.jobs.events.- On matching
jobIdevent: return status JSON (certificate / receipt). - On timeout:
{ status: pending, jobId }so the REST Hook can finish the Zap.
includeAttached: after seal, aggregator should verae.archive.query; bloom hits merge extra receipts. Simulator does this; live aggregator hook is TBD.
4. Push back to Zapier
- Wait response: HTTP body on the same Zap step.
- REST Hook: Zapier subscribes
POST /zapier/v1/hooks. Onjobs.events, middleware enqueuesverae.zapier.webhooks.deliver. Worker POSTstargetUrl(hooks.zapier.com). - Poll status: Zap action Find Job Status →
GET /zapier/v1/status/{jobId}→ middlewareGETVerae (or last event).
5. Verify
POST /zapier/v1/verify → middleware → Verae POST /api/verify. No job watch.
Connect live api.veraetime.net
Still blocked on operator bind credentials. When ready:
# middleware env
MOCK_VERAE=false
VERAE_API_BASE_URL=https://api.veraetime.net
NATS_ENABLED=true
NATS_URL=nats://10.10.10.21:4222,nats://10.10.10.22:4222,nats://10.10.10.23:4222
JETSTREAM_REPLICAS=3
Then: working Verae login, one live seal, confirm 202/status/verify, map receipt fields, REST Hook to a private Zap. See zapier-decisions/STATUS.md “Once MOCK_VERAE=false”.
Billing on this path
Designed: edge meters usage.recorded → account-balance; 402 if prepaid empty.
Running: middleware local usage files; account-balance NATS is up for portal/CS. Wire edge meter → verae.billing.usage.recorded and 402 from books is still a finish item.