verdifax 0.3.0 → 1.0.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.
package/dist/index.mjs CHANGED
@@ -127,6 +127,49 @@ function requestKeyRegistrationBody(signingKey) {
127
127
  return { public_key, proof };
128
128
  }
129
129
 
130
+ // src/helpers.ts
131
+ function formatProviderPayload(provider, prompt, response) {
132
+ if ([provider, prompt, response].some((text) => /[\uD800-\uDFFF]/u.test(text))) {
133
+ throw new VerdifaxError(
134
+ "verdifax: provider payload text cannot be encoded as UTF-8"
135
+ );
136
+ }
137
+ return JSON.stringify({ prompt, provider, response });
138
+ }
139
+ function isProvided(value) {
140
+ return value !== null && value !== void 0 && value !== "" && value !== false;
141
+ }
142
+ function withAttestedFlag(context) {
143
+ const provided = Object.entries(context).some(
144
+ ([name, value]) => name !== "attested" && isProvided(value)
145
+ );
146
+ return { ...context, attested: provided };
147
+ }
148
+ function withDeclaredFlag(context) {
149
+ const declared = Object.entries(context).some(
150
+ ([name, value]) => name !== "declared" && isProvided(value) && !(Array.isArray(value) && value.length === 0)
151
+ );
152
+ return { ...context, declared };
153
+ }
154
+ function refuseCallerOriginHashes(substance) {
155
+ const origin = substance?.origin;
156
+ if (origin?.source_ip_hash || origin?.user_agent_hash) {
157
+ throw new VerdifaxError(
158
+ "verdifax: request_substance.origin.source_ip_hash and user_agent_hash are computed by the server and cannot be supplied"
159
+ );
160
+ }
161
+ }
162
+ function withExecuteFlags(req) {
163
+ const body = { ...req };
164
+ if (req.attested_context) {
165
+ body.attested_context = withAttestedFlag(req.attested_context);
166
+ }
167
+ if (req.reproducibility_context) {
168
+ body.reproducibility_context = withDeclaredFlag(req.reproducibility_context);
169
+ }
170
+ return body;
171
+ }
172
+
130
173
  // src/validation.ts
131
174
  function validateHex64(value, fieldName) {
132
175
  if (typeof value !== "string" || value.length !== 64) {
@@ -157,7 +200,7 @@ function validateRouteId(value) {
157
200
  }
158
201
 
159
202
  // src/version.ts
160
- var SDK_VERSION = "0.3.0";
203
+ var SDK_VERSION = "1.0.0";
161
204
 
162
205
  // src/client.ts
163
206
  var DEFAULT_BASE_URL = "https://api.verdifax.com";
@@ -167,7 +210,10 @@ var DEFAULT_RETRY_BASE_DELAY_MS = 200;
167
210
  var SDK_USER_AGENT = `verdifax-sdk-node/${SDK_VERSION}`;
168
211
  var HEADER_API_KEY = "X-Verdifax-Key";
169
212
  var REQUEST_KEY_PATH = "/keys/request-key";
213
+ var HEADER_EXPORT_TOTAL = "X-Verdifax-Total";
214
+ var HEADER_EXPORT_TRUNCATED = "X-Verdifax-Truncated";
170
215
  var RETRYABLE_STATUSES = /* @__PURE__ */ new Set([429, 502, 503, 504]);
216
+ var MAX_BATCH_ROWS = 1e3;
171
217
  var VerdifaxClient = class {
172
218
  baseURL;
173
219
  apiKey;
@@ -192,21 +238,52 @@ var VerdifaxClient = class {
192
238
  async version() {
193
239
  return this.request("GET", "/version");
194
240
  }
241
+ /** The server's own API description. */
242
+ async getOpenAPI() {
243
+ return this.request("GET", "/openapi.json");
244
+ }
245
+ /** Run counts for this API key. */
246
+ async getStats() {
247
+ this.requireAPIKey();
248
+ return this.request("GET", "/stats");
249
+ }
195
250
  // ── Execute / Attest (auth) ───────────────────────────────────
196
251
  async execute(req) {
252
+ this.requireExecuteFields(req);
253
+ return this.request("POST", "/execute", this.prepared(req));
254
+ }
255
+ /** Runs one payload twice on the server and compares the manifest
256
+ * hashes. One signature covers the request, and the server claims
257
+ * its nonce once. Both runs are recorded. */
258
+ async verifyDeterminism(req) {
259
+ this.requireExecuteFields(req);
260
+ return this.request(
261
+ "POST",
262
+ "/execute/verify-determinism",
263
+ this.prepared(req)
264
+ );
265
+ }
266
+ /** Sends up to {@link MAX_BATCH_ROWS} runs in one request. With a
267
+ * signing key each row carries its own signature and nonce. A row
268
+ * that fails comes back in `results` with `ok: false`, so the call
269
+ * does not throw for it. The rows are not checked here: the server
270
+ * reports a bad row in that row's result.
271
+ *
272
+ * This is one POST and it is never retried. After a timeout the
273
+ * server may have run some or all of the rows. */
274
+ async executeBatch(runs) {
197
275
  this.requireAPIKey();
198
- if (!req.payload && !req.payload_text) {
199
- throw new VerdifaxError(
200
- "verdifax: ExecuteRequest needs payload or payload_text"
201
- );
276
+ if (!Array.isArray(runs) || runs.length === 0) {
277
+ throw new VerdifaxError("verdifax: executeBatch needs at least one run");
202
278
  }
203
- if (!req.program_id || !req.route_id || !req.registry_record_hash) {
279
+ if (runs.length > MAX_BATCH_ROWS) {
204
280
  throw new VerdifaxError(
205
- "verdifax: program_id, route_id, and registry_record_hash are required"
281
+ `verdifax: executeBatch accepts at most ${MAX_BATCH_ROWS} runs (got ${runs.length})`
206
282
  );
207
283
  }
208
- const body = this.signingKey ? { ...req, request_signature: signRequest(this.signingKey, req) } : req;
209
- return this.request("POST", "/execute", body);
284
+ return this.request("POST", "/execute/batch", {
285
+ runs: runs.map((run) => this.prepared(run))
286
+ });
210
287
  }
211
288
  /** High-level convenience wrapper around `execute()`. Accepts
212
289
  * either a Buffer (for binary payloads, auto-base64) or a
@@ -232,7 +309,12 @@ var VerdifaxClient = class {
232
309
  route_id: req.route_id,
233
310
  registry_record_hash: req.registry_record_hash,
234
311
  ai_output_text: req.ai_output_text,
235
- attested_context: req.attested_context
312
+ attested_context: req.attested_context,
313
+ reproducibility_context: req.reproducibility_context,
314
+ request_substance: req.request_substance,
315
+ authorization_chain: req.authorization_chain,
316
+ regulatory_scaffolding: req.regulatory_scaffolding,
317
+ causal_graph: req.causal_graph
236
318
  };
237
319
  if (req.payload !== void 0) {
238
320
  body.payload = Buffer.isBuffer(req.payload) ? req.payload.toString("base64") : Buffer.from(req.payload).toString("base64");
@@ -289,6 +371,94 @@ var VerdifaxClient = class {
289
371
  const out = await this.request("GET", path);
290
372
  return { runs: out.runs ?? [], total: out.total ?? 0 };
291
373
  }
374
+ /** Searches this key's runs. `manifest_hash` matches a prefix. The
375
+ * server ignores a `from` or `to` it cannot parse here, unlike
376
+ * {@link exportRuns}, which refuses one. */
377
+ async searchRuns(params = {}) {
378
+ this.requireAPIKey();
379
+ const q = new URLSearchParams();
380
+ for (const name of [
381
+ "manifest_hash",
382
+ "program_id",
383
+ "route_id",
384
+ "status",
385
+ "from",
386
+ "to"
387
+ ]) {
388
+ const value = params[name];
389
+ if (value) q.set(name, value);
390
+ }
391
+ if (params.limit && params.limit > 0) {
392
+ q.set("limit", String(params.limit));
393
+ }
394
+ if (params.offset && params.offset > 0) {
395
+ q.set("offset", String(params.offset));
396
+ }
397
+ const qs = q.toString();
398
+ const path = qs ? `/runs/search?${qs}` : "/runs/search";
399
+ const out = await this.request("GET", path);
400
+ return { runs: out.runs ?? [], total: out.total ?? 0 };
401
+ }
402
+ /** Lists what the server holds for this key in a period, failures
403
+ * included, up to 10,000 rows. `truncated` is true when the period
404
+ * holds more. The list states what was stored, not a verdict, and a
405
+ * call that never reached Verdifax cannot appear in it. */
406
+ async exportRuns(params = {}) {
407
+ this.requireAPIKey();
408
+ return this.request("GET", this.exportPath(params, "json"));
409
+ }
410
+ /** The same rows as {@link exportRuns}: the raw CSV text with `total`
411
+ * and `truncated` from the response headers. Check `truncated`: when
412
+ * true, the CSV is missing rows for the period. Throws when the server
413
+ * does not send those headers, so that a cut-off export cannot pass
414
+ * for a complete one. */
415
+ async exportRunsCSV(params = {}) {
416
+ this.requireAPIKey();
417
+ const { text, headers } = await this.requestRaw(
418
+ this.exportPath(params, "csv")
419
+ );
420
+ const total = Number.parseInt(headers.get(HEADER_EXPORT_TOTAL) ?? "", 10);
421
+ const truncated = headers.get(HEADER_EXPORT_TRUNCATED);
422
+ if (!Number.isSafeInteger(total) || truncated !== "true" && truncated !== "false") {
423
+ throw new VerdifaxError(
424
+ `verdifax: the server did not report ${HEADER_EXPORT_TOTAL} and ${HEADER_EXPORT_TRUNCATED}, so this CSV may be cut off; use exportRuns instead`
425
+ );
426
+ }
427
+ return { csv: text, total, truncated: truncated === "true" };
428
+ }
429
+ exportPath(params, format) {
430
+ const q = new URLSearchParams();
431
+ if (params.from) q.set("from", params.from);
432
+ if (params.to) q.set("to", params.to);
433
+ q.set("format", format);
434
+ return `/runs/export?${q.toString()}`;
435
+ }
436
+ // ── Attestation receipts (auth) ──────────────────────────────
437
+ async listAttestations(params = {}) {
438
+ this.requireAPIKey();
439
+ const q = new URLSearchParams();
440
+ if (params.limit && params.limit > 0) {
441
+ q.set("limit", String(params.limit));
442
+ }
443
+ if (params.offset && params.offset > 0) {
444
+ q.set("offset", String(params.offset));
445
+ }
446
+ const qs = q.toString();
447
+ return this.request(
448
+ "GET",
449
+ qs ? `/attestations?${qs}` : "/attestations"
450
+ );
451
+ }
452
+ async getAttestation(attestationId) {
453
+ this.requireAPIKey();
454
+ if (attestationId <= 0) {
455
+ throw new VerdifaxError("verdifax: attestationId must be > 0");
456
+ }
457
+ return this.request(
458
+ "GET",
459
+ `/attestations/${attestationId}`
460
+ );
461
+ }
292
462
  // ── Sealed-artifact retrieval (auth) ─────────────────────────
293
463
  async getAllowToken(runId) {
294
464
  return this.getRunArtifact(runId, "allow-token");
@@ -305,6 +475,39 @@ var VerdifaxClient = class {
305
475
  async getAivpT4HaltReceipt(runId) {
306
476
  return this.getRunArtifact(runId, "aivp-t4-halt-receipt");
307
477
  }
478
+ async getAttestationGapReceipt(runId) {
479
+ return this.getRunArtifact(runId, "attestation-gap-receipt");
480
+ }
481
+ async getCESAuditRecord(runId) {
482
+ return this.getRunArtifact(runId, "ces-audit-record");
483
+ }
484
+ /** The audit report for a run, as JSON. */
485
+ async getRunReport(runId) {
486
+ const out = await this.getRunArtifact(runId, "report");
487
+ return out.report;
488
+ }
489
+ /** The run's sealed audit bundle as the exact JSON text the server
490
+ * sent, to save and check with `verdifax-verify`. It is not parsed:
491
+ * JSON.parse would round a number above 2^53 and the recomputed hash
492
+ * would stop matching. */
493
+ async getRunArtifacts(runId) {
494
+ this.requireAPIKey();
495
+ if (runId <= 0) throw new VerdifaxError("verdifax: runId must be > 0");
496
+ return (await this.requestRaw(`/runs/${runId}/artifacts`)).text;
497
+ }
498
+ /** The public audit bundle of a record published by run id, as the
499
+ * exact JSON text the server sent. Needs no API key. */
500
+ async getPublicBundle(runId) {
501
+ if (runId <= 0) throw new VerdifaxError("verdifax: runId must be > 0");
502
+ return (await this.requestRaw(`/runs/${runId}/bundle.json`)).text;
503
+ }
504
+ /** The public audit bundle a share token points to, as the exact JSON
505
+ * text the server sent. Needs no API key. */
506
+ async getPublicBundleByToken(token) {
507
+ if (!token) throw new VerdifaxError("verdifax: token is required");
508
+ const path = `/public/runs/${encodeURIComponent(token)}/bundle.json`;
509
+ return (await this.requestRaw(path)).text;
510
+ }
308
511
  async getRunArtifact(runId, suffix) {
309
512
  this.requireAPIKey();
310
513
  if (runId <= 0) throw new VerdifaxError("verdifax: runId must be > 0");
@@ -391,13 +594,15 @@ var VerdifaxClient = class {
391
594
  await this.request("DELETE", `/admin/keys/${keyId}`);
392
595
  }
393
596
  // ── Provider helpers (Claude / OpenAI) ───────────────────────
394
- /** Convenience for attesting an Anthropic Claude API response.
395
- * Wires the response text into the AIVP governance pipeline
396
- * by setting `ai_output_text`. */
597
+ /** Convenience for attesting an Anthropic Claude API response. With
598
+ * `govern: true` the response text also goes to the AIVP review as
599
+ * `ai_output_text`; that is off by default, so the text leaves your
600
+ * machine for review only when you ask. */
397
601
  async attestClaudeResponse(args) {
398
602
  return this.attestProviderResponse({ ...args, provider: "anthropic" });
399
603
  }
400
- /** Convenience for attesting an OpenAI API response. */
604
+ /** Convenience for attesting an OpenAI API response. `govern` works as
605
+ * in {@link attestClaudeResponse}. */
401
606
  async attestOpenAIResponse(args) {
402
607
  return this.attestProviderResponse({ ...args, provider: "openai" });
403
608
  }
@@ -407,17 +612,16 @@ var VerdifaxClient = class {
407
612
  "verdifax: response is required for attestation"
408
613
  );
409
614
  }
410
- const payloadText = JSON.stringify({
411
- provider: args.provider,
412
- prompt: args.prompt,
413
- response: args.response
414
- });
415
615
  return this.attest({
416
- payload_text: payloadText,
616
+ payload_text: formatProviderPayload(
617
+ args.provider,
618
+ args.prompt,
619
+ args.response
620
+ ),
417
621
  program_id: args.program_id,
418
622
  route_id: args.route_id,
419
623
  registry_record_hash: args.registry_record_hash,
420
- ai_output_text: args.response,
624
+ ai_output_text: args.govern ? args.response : void 0,
421
625
  attested_context: {
422
626
  actor_role: "ai_assistant",
423
627
  model_provider: args.provider
@@ -425,7 +629,7 @@ var VerdifaxClient = class {
425
629
  });
426
630
  }
427
631
  // ── HTTP plumbing, retry-aware ──────────────────────────────
428
- async request(method, path, body) {
632
+ async request(method, path, body, rawText = false) {
429
633
  const url = this.baseURL + path;
430
634
  const headers = {
431
635
  "User-Agent": this.userAgent
@@ -482,6 +686,7 @@ var VerdifaxClient = class {
482
686
  throw new APIError(resp.status, path, errMessage);
483
687
  }
484
688
  }
689
+ if (rawText) return { text, headers: resp.headers };
485
690
  if (text.length === 0) return void 0;
486
691
  try {
487
692
  return JSON.parse(text);
@@ -495,17 +700,44 @@ var VerdifaxClient = class {
495
700
  `verdifax: retry budget exhausted${lastErr ? `: ${String(lastErr)}` : ""}`
496
701
  );
497
702
  }
703
+ /** A GET whose body is kept as sent, retried like any other GET. */
704
+ requestRaw(path) {
705
+ return this.request("GET", path, void 0, true);
706
+ }
498
707
  requireAPIKey() {
499
708
  if (!this.apiKey) throw new APIKeyRequiredError();
500
709
  }
710
+ requireExecuteFields(req) {
711
+ this.requireAPIKey();
712
+ if (!req.payload && !req.payload_text) {
713
+ throw new VerdifaxError(
714
+ "verdifax: ExecuteRequest needs payload or payload_text"
715
+ );
716
+ }
717
+ if (!req.program_id || !req.route_id || !req.registry_record_hash) {
718
+ throw new VerdifaxError(
719
+ "verdifax: program_id, route_id, and registry_record_hash are required"
720
+ );
721
+ }
722
+ validateHex64(req.program_id, "program_id");
723
+ validateHex64(req.registry_record_hash, "registry_record_hash");
724
+ validateRouteId(req.route_id);
725
+ refuseCallerOriginHashes(req.request_substance);
726
+ }
727
+ /** The request with its derived flags and, with a signing key, a fresh
728
+ * signature and nonce, on a copy. */
729
+ prepared(req) {
730
+ const body = withExecuteFlags(req);
731
+ return this.signingKey ? { ...body, request_signature: signRequest(this.signingKey, body) } : body;
732
+ }
501
733
  };
502
734
 
503
735
  // src/config.ts
504
736
  function fromEnv() {
505
737
  const cfg = {
506
- baseURL: process.env.VERDIFAX_BASE_URL ?? void 0,
738
+ baseURL: process.env.VERDIFAX_BASE_URL || process.env.VERDIFAX_API_URL || void 0,
507
739
  apiKey: process.env.VERDIFAX_API_KEY ?? void 0,
508
- userAgent: process.env.VERDIFAX_USER_AGENT ?? void 0
740
+ userAgent: process.env.VERDIFAX_USER_AGENT || void 0
509
741
  };
510
742
  const timeoutRaw = process.env.VERDIFAX_TIMEOUT_MS;
511
743
  if (timeoutRaw !== void 0 && timeoutRaw !== "") {
@@ -529,13 +761,176 @@ function fromEnv() {
529
761
  }
530
762
  return new VerdifaxClient(cfg);
531
763
  }
764
+
765
+ // src/environment.ts
766
+ import { execFileSync } from "child_process";
767
+ import { readdirSync, readFileSync } from "fs";
768
+ import { join } from "path";
769
+ var HASH_64 = /^[0-9a-f]{64}$/;
770
+ var GIT_SHA = /^([0-9a-f]{40}|[0-9a-f]{64})$/;
771
+ var PLATFORM_NAMES = { win32: "windows" };
772
+ var ARCH_NAMES = { x64: "amd64", ia32: "386" };
773
+ function packageVersion(dir) {
774
+ try {
775
+ const pkg = JSON.parse(readFileSync(join(dir, "package.json"), "utf8"));
776
+ return pkg.name && pkg.version ? `${pkg.name}==${pkg.version}` : void 0;
777
+ } catch {
778
+ return void 0;
779
+ }
780
+ }
781
+ function packageDirs(root) {
782
+ const dirs = [];
783
+ for (const entry of readdirSync(root)) {
784
+ if (entry.startsWith(".")) continue;
785
+ if (!entry.startsWith("@")) {
786
+ dirs.push(join(root, entry));
787
+ continue;
788
+ }
789
+ for (const scoped of readdirSync(join(root, entry))) {
790
+ dirs.push(join(root, entry, scoped));
791
+ }
792
+ }
793
+ return dirs;
794
+ }
795
+ function detectDependencies() {
796
+ try {
797
+ const pins = packageDirs(join(process.cwd(), "node_modules")).map(packageVersion).filter((pin) => pin !== void 0);
798
+ pins.sort((a, b) => a.toLowerCase().localeCompare(b.toLowerCase()));
799
+ return pins.length > 0 ? pins : void 0;
800
+ } catch {
801
+ return void 0;
802
+ }
803
+ }
804
+ function detectGitSHA() {
805
+ try {
806
+ const sha = execFileSync("git", ["rev-parse", "HEAD"], {
807
+ encoding: "utf8",
808
+ stdio: ["ignore", "pipe", "ignore"],
809
+ timeout: 2e3
810
+ }).trim().toLowerCase();
811
+ return GIT_SHA.test(sha) ? sha : void 0;
812
+ } catch {
813
+ return void 0;
814
+ }
815
+ }
816
+ function detectContainerHash() {
817
+ try {
818
+ const text = readFileSync("/proc/self/cgroup", "utf8");
819
+ return text.split("\n").flatMap((line) => line.split("/")).map((segment) => segment.trim()).find((segment) => HASH_64.test(segment));
820
+ } catch {
821
+ return void 0;
822
+ }
823
+ }
824
+ function captureEnvironment(options = {}) {
825
+ const seeds = Object.entries(options.declaredSeeds ?? {}).map(([name, seed]) => `${name}=${seed}`).sort();
826
+ const pinned = options.includeDependencies === false ? void 0 : detectDependencies();
827
+ const git = options.includeGit === false ? void 0 : detectGitSHA();
828
+ const container = options.includeContainer === false ? void 0 : detectContainerHash();
829
+ const os = PLATFORM_NAMES[process.platform] ?? process.platform;
830
+ const arch = ARCH_NAMES[process.arch] ?? process.arch;
831
+ return {
832
+ declared: true,
833
+ runtime_name: "node",
834
+ runtime_version: process.versions.node,
835
+ platform: `${os}/${arch}`,
836
+ ...pinned ? { pinned_dependencies: pinned } : {},
837
+ ...git ? { git_commit_sha: git } : {},
838
+ ...container ? { container_image_hash: container } : {},
839
+ ...seeds.length > 0 ? { random_seeds: seeds } : {}
840
+ };
841
+ }
842
+
843
+ // src/types.ts
844
+ var RUN_STATUSES = [
845
+ "ok",
846
+ "probe",
847
+ "pepg_deny",
848
+ "ccv_halt",
849
+ "macc_halt",
850
+ "aivp_t4_halt",
851
+ "attestation_gap",
852
+ "stage_error"
853
+ ];
854
+
855
+ // src/section0.ts
856
+ import { createHash as createHash2 } from "crypto";
857
+ var DSE_FORMULA_VERSION = "dse.tcu.dispatch.v1";
858
+ var DCAE_PREIMAGE_VERSION = "verdifax.dcae.v1";
859
+ var CRES_PREIMAGE_VERSION = "verdifax.cres.v1";
860
+ var CRES_ENGINE_VERSION = "verdifax-cres/1.0.0";
861
+ function sha256Hex(preimage) {
862
+ return createHash2("sha256").update(Buffer.from(preimage, "utf8")).digest("hex");
863
+ }
864
+ function requireHex64(value, name) {
865
+ try {
866
+ validateHex64(value, name);
867
+ } catch (err) {
868
+ throw new VerdifaxError(
869
+ `verdifax: section0: ${err instanceof Error ? err.message : String(err)}`
870
+ );
871
+ }
872
+ }
873
+ function dseDispatchHash(fields) {
874
+ requireHex64(fields.program_id, "program_id");
875
+ requireHex64(fields.registry_record_hash, "registry_record_hash");
876
+ return sha256Hex(
877
+ [
878
+ DSE_FORMULA_VERSION,
879
+ fields.envelope_id,
880
+ fields.sequence_id,
881
+ fields.program_id,
882
+ fields.registry_record_hash
883
+ ].join(".")
884
+ );
885
+ }
886
+ function dcaeClosureHash(fields) {
887
+ requireHex64(fields.manifest_hash, "manifest_hash");
888
+ requireHex64(fields.aer_hash, "aer_hash");
889
+ requireHex64(fields.zksp_binding_hash, "zksp_binding_hash");
890
+ return sha256Hex(
891
+ [
892
+ DCAE_PREIMAGE_VERSION,
893
+ fields.manifest_hash,
894
+ fields.aer_hash,
895
+ fields.envelope_id,
896
+ fields.zksp_binding_hash,
897
+ fields.formal_verifier_status
898
+ ].join("|")
899
+ );
900
+ }
901
+ function cresReceiptHash(fields) {
902
+ requireHex64(fields.ciphertext_hash_at_shred, "ciphertext_hash_at_shred");
903
+ return sha256Hex(
904
+ [
905
+ CRES_PREIMAGE_VERSION,
906
+ fields.envelope_id,
907
+ fields.field_path,
908
+ fields.deletion_clock,
909
+ fields.actor_id,
910
+ fields.ciphertext_hash_at_shred,
911
+ fields.dsar_reference,
912
+ fields.engine_version ?? CRES_ENGINE_VERSION
913
+ ].join("|")
914
+ );
915
+ }
532
916
  export {
533
917
  APIError,
534
918
  APIKeyRequiredError,
535
919
  AuthError,
920
+ CRES_ENGINE_VERSION,
921
+ CRES_PREIMAGE_VERSION,
922
+ DCAE_PREIMAGE_VERSION,
923
+ DSE_FORMULA_VERSION,
924
+ MAX_BATCH_ROWS,
536
925
  NotFoundError,
926
+ RUN_STATUSES,
537
927
  VerdifaxClient,
538
928
  VerdifaxError,
929
+ captureEnvironment,
930
+ cresReceiptHash,
931
+ dcaeClosureHash,
932
+ dseDispatchHash,
933
+ formatProviderPayload,
539
934
  fromEnv,
540
935
  generateRequestKeyPair,
541
936
  requestKeyRegistrationBody,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "verdifax",
3
- "version": "0.3.0",
3
+ "version": "1.0.0",
4
4
  "description": "Official Node.js / TypeScript SDK for the Verdifax orchestrator REST API.",
5
5
  "license": "MIT",
6
6
  "author": "Verdifax <team@verdifax.com>",