@v0uch/sdk
v0.1.0
Published
Typed SDK for proof-backed Vouch sensor verification.
Maintainers
Readme
@v0uch/sdk
Typed protocol utilities and an HTTP client for Vouch proof-backed sensor verification.
0.1.0is an experimental testnet release. Public APIs may change before1.0.0.
Install
npm install @v0uch/sdkThe package is ESM-only and supports Node.js 20+, modern browsers, and
Expo/React Native. It uses the runtime's standards-based Fetch API; pass a
custom fetch implementation when your runtime or tests require one.
Create a client
import { createVouchClient } from "@v0uch/sdk";
const vouch = createVouchClient({
baseUrl: "https://api.example.com",
});
const health = await vouch.health();
console.log(health.ok, health.mode);baseUrl must be a bare HTTP or HTTPS origin. Credentials, paths, query
parameters, and fragments are rejected before a request is sent.
Run a verification session
Create a session and register a device:
const { sessionId, joinCode } = await vouch.createSession();
await vouch.registerDevice({
deviceId: "device-a",
displayName: "Phone A",
payoutAccountId: "0.0.1001",
});
await vouch.joinSession({
joinCode,
deviceId: "device-a",
});Create a challenge, upload a sensor batch, and read the result:
const challenge = await vouch.createChallenge(sessionId, {
requestedKind: "shake",
});
const result = await vouch.uploadBatch({
payload: {
schemaVersion: "1",
sessionId,
challengeId: challenge.id,
challengeNonce: challenge.nonce,
integrityChallenge: "app-attest-assertion-challenge",
deviceId: "device-a",
startedAtMs: challenge.startAtMs,
nominalHz: 50,
accelerometer: [],
gyroscope: [],
faultMode: "none",
},
});
console.log(result.status, result.verdicts);The verifier, rather than the client, remains authoritative for evidence acceptance, health scoring, and reward authorization.
App Attest boundary
The SDK transports App Attest challenges, attestations, and registration status, but does not create native keys or assertions. An iOS application must use its native App Attest integration and pass the portable strings to:
const integrity = await vouch.createIntegrityChallenge(
"device-a",
"attestation",
);
await vouch.registerAppAttestation({
deviceId: "device-a",
keyId: "native-key-id",
attestationBase64: "base64-attestation",
challenge: integrity.challenge,
});This keeps the package portable and prevents Expo or Apple-native dependencies from entering Node and browser builds.
Schemas and types
All HTTP responses are validated with the same exported Zod schemas used by the Vouch applications:
import {
PublicSessionSchema,
type PublicSession,
} from "@v0uch/sdk";
const session: PublicSession = PublicSessionSchema.parse(untrustedJson);The package exports the challenge, device, sensor-batch, verdict, evidence, audit, settlement, Hedera metadata, and 0G metadata schemas and their inferred TypeScript types.
Canonical proof bytes
Use the portable RFC 8785 JSON canonicalization and SHA-256 helpers when constructing or checking proof bindings:
import {
canonicalBytes,
canonicalize,
sha256Hex,
} from "@v0uch/sdk";
const payload = { sessionId: "session-1", status: "COMPLETE" };
const canonicalJson = canonicalize(payload);
const digest = sha256Hex(canonicalBytes(payload));
console.log(canonicalJson, digest);Non-finite numbers, cyclic objects, and values that cannot be represented as canonical JSON are rejected.
Typed errors and cancellation
import { VouchApiError } from "@v0uch/sdk";
try {
await vouch.getSession("missing-session");
} catch (error) {
if (error instanceof VouchApiError) {
console.error(error.code, error.status, error.retryable);
}
}Typed server errors preserve their public code and HTTP status. Transport
failures become retryable NETWORK_ERROR values. Caller-triggered aborts remain
AbortError values so applications can distinguish cancellation from network
failure.
Every operation that waits on the network accepts an optional
{ signal: AbortSignal } argument.
Testing utilities
Development-only utilities use a separate entry point:
import {
createVouchDemoClient,
makeThreeDeviceFixture,
} from "@v0uch/sdk/testing";
const demo = createVouchDemoClient({
baseUrl: "http://127.0.0.1:8787",
});
const fixture = makeThreeDeviceFixture("device-c-freeze");
console.log(demo, fixture);createVouchDemoClient exposes the simulated-device route used by the local
showcase. Production integrations should import createVouchClient from the
package root.
Security and network status
- Vouch rewards and ledger records in this release use test networks.
- Testnet rewards are not presented as income or assets with monetary value.
- Never put Hedera, 0G, or other private keys in client applications.
- The SDK does not verify raw sensor evidence locally; it submits typed payloads to the configured verifier.
- Publishing this SDK does not make a verifier deployment safe for untrusted public traffic. Operators must separately configure authentication, rate limits, persistence, secrets, CORS, and TLS.
Development and releases
Source and architecture documentation live in the Vouch repository.
Before publishing:
npm run release:check -w @v0uch/sdkThe first public release is published manually with npm 2FA. Later releases use
the repository's npm trusted-publishing workflow and matching sdk-v<version>
tags.
After 0.1.0 exists on npm, configure its trusted publisher with:
- provider: GitHub Actions;
- GitHub owner:
fac3m4n; - repository:
vouch; - workflow filename:
release-sdk.yml; - allowed action:
npm publish.
For later versions, commit the matching package version and push a tag such as
sdk-v0.1.1. The workflow rejects tags that do not exactly match
packages/protocol/package.json.
License
MIT
