@zktable/circuits 0.1.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/LICENSE +21 -0
- package/README.md +40 -0
- package/card_membership/Nargo.toml +8 -0
- package/card_membership/src/main.nr +106 -0
- package/dice_valid/Nargo.toml +8 -0
- package/dice_valid/src/main.nr +104 -0
- package/dist/index.cjs +304 -0
- package/dist/index.d.cts +89 -0
- package/dist/index.d.ts +89 -0
- package/dist/index.js +265 -0
- package/move_along/Nargo.toml +8 -0
- package/move_along/fixtures/test_graph.json +13 -0
- package/move_along/src/main.nr +73 -0
- package/move_along/target/move_along.json +1 -0
- package/move_along/target/vk +0 -0
- package/move_along/target/vk_fields.json +1 -0
- package/package.json +42 -0
- package/scripts/build_all.sh +174 -0
- package/scripts/build_one.sh +11 -0
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
type Ticket = 0 | 1 | 2;
|
|
2
|
+
type GraphEdge = {
|
|
3
|
+
from: number;
|
|
4
|
+
to: number;
|
|
5
|
+
ticket: Ticket;
|
|
6
|
+
};
|
|
7
|
+
type GraphData = {
|
|
8
|
+
nodes: number[];
|
|
9
|
+
edges: GraphEdge[];
|
|
10
|
+
/** Expand each edge to both directions. Defaults to true. */
|
|
11
|
+
bidirectional?: boolean;
|
|
12
|
+
};
|
|
13
|
+
type BoardMove = {
|
|
14
|
+
from: number;
|
|
15
|
+
to: number;
|
|
16
|
+
ticket: Ticket;
|
|
17
|
+
saltOld: bigint;
|
|
18
|
+
saltNew: bigint;
|
|
19
|
+
};
|
|
20
|
+
type BoardProof = {
|
|
21
|
+
/** UltraHonk proof bytes (14592 bytes). */
|
|
22
|
+
proof: Uint8Array;
|
|
23
|
+
/** c_old | c_new | ticket | root, 32 bytes each = 128 bytes total. */
|
|
24
|
+
publicInputs: Uint8Array;
|
|
25
|
+
cOld: string;
|
|
26
|
+
cNew: string;
|
|
27
|
+
root: string;
|
|
28
|
+
ticket: Ticket;
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* A public transit graph. Wraps the `zktable-graph` Rust CLI for the
|
|
33
|
+
* hash-dependent operations (edge-tree root, Poseidon commitments) and does
|
|
34
|
+
* pure, local edge-membership checks in TS.
|
|
35
|
+
*/
|
|
36
|
+
declare class BoardGraph {
|
|
37
|
+
readonly data: GraphData;
|
|
38
|
+
private readonly graphToolsBin;
|
|
39
|
+
private readonly edges;
|
|
40
|
+
constructor(data: GraphData, opts?: {
|
|
41
|
+
graphToolsBin?: string;
|
|
42
|
+
});
|
|
43
|
+
/** Pure, local check: is (from, to, ticket) a legal edge of this graph? */
|
|
44
|
+
hasEdge(from: number, to: number, ticket: Ticket): boolean;
|
|
45
|
+
/** Edge-tree root (hex), via `zktable-graph root`. */
|
|
46
|
+
root(): Promise<string>;
|
|
47
|
+
/** Poseidon2(node, salt) (hex), via `zktable-graph commit`. */
|
|
48
|
+
commit(node: number, salt: bigint): Promise<string>;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
type BoardProverOptions = {
|
|
52
|
+
circuitDir?: string;
|
|
53
|
+
graphToolsBin?: string;
|
|
54
|
+
nargoBin?: string;
|
|
55
|
+
bbBin?: string;
|
|
56
|
+
workDir?: string;
|
|
57
|
+
};
|
|
58
|
+
/**
|
|
59
|
+
* Orchestrates the full `board` module pipeline against real tools: writes
|
|
60
|
+
* the graph, builds the witness via `zktable-graph`, executes the circuit
|
|
61
|
+
* via `nargo`, and proves/verifies via `bb`. No mocks — every call produces
|
|
62
|
+
* or checks a real UltraHonk proof.
|
|
63
|
+
*/
|
|
64
|
+
declare class BoardProver {
|
|
65
|
+
private readonly circuitDir;
|
|
66
|
+
private readonly graphToolsBin;
|
|
67
|
+
private readonly nargoBin;
|
|
68
|
+
private readonly bbBin;
|
|
69
|
+
private readonly workDir;
|
|
70
|
+
private readonly env;
|
|
71
|
+
constructor(opts?: BoardProverOptions);
|
|
72
|
+
private get targetDir();
|
|
73
|
+
private get bytecodePath();
|
|
74
|
+
private get vkPath();
|
|
75
|
+
/** Compile the circuit once if `target/move_along.json` is missing. */
|
|
76
|
+
private ensureCompiled;
|
|
77
|
+
/** Generate the verification key once if `target/vk` is missing. */
|
|
78
|
+
private ensureVk;
|
|
79
|
+
/**
|
|
80
|
+
* Full pipeline: write graph -> `zktable-graph witness` -> `nargo execute`
|
|
81
|
+
* -> `bb prove`. Runs entirely inside an isolated temp dir; never touches
|
|
82
|
+
* `move_along/Prover.toml` or `move_along/target/`.
|
|
83
|
+
*/
|
|
84
|
+
prove(graph: GraphData, move: BoardMove): Promise<BoardProof>;
|
|
85
|
+
/** Off-chain check via `bb verify`. */
|
|
86
|
+
verifyLocally(proof: BoardProof): Promise<boolean>;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
export { BoardGraph, type BoardMove, type BoardProof, BoardProver, type BoardProverOptions, type GraphData, type GraphEdge, type Ticket };
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,265 @@
|
|
|
1
|
+
// src/graph.ts
|
|
2
|
+
import { execFile } from "child_process";
|
|
3
|
+
import { mkdtemp, rm, writeFile } from "fs/promises";
|
|
4
|
+
import os2 from "os";
|
|
5
|
+
import path2 from "path";
|
|
6
|
+
import { promisify } from "util";
|
|
7
|
+
|
|
8
|
+
// src/paths.ts
|
|
9
|
+
import os from "os";
|
|
10
|
+
import path from "path";
|
|
11
|
+
import { fileURLToPath } from "url";
|
|
12
|
+
var here = path.dirname(fileURLToPath(import.meta.url));
|
|
13
|
+
var PACKAGE_ROOT = path.resolve(here, "..");
|
|
14
|
+
var DEFAULT_CIRCUIT_DIR = path.join(PACKAGE_ROOT, "move_along");
|
|
15
|
+
var CIRCUIT_PACKAGE_NAME = "move_along";
|
|
16
|
+
var DEFAULT_GRAPH_TOOLS_BIN = path.resolve(
|
|
17
|
+
PACKAGE_ROOT,
|
|
18
|
+
"../contracts/tools/graph-tools/target/release/zktable-graph"
|
|
19
|
+
);
|
|
20
|
+
var DEFAULT_NARGO_BIN = "nargo";
|
|
21
|
+
var DEFAULT_BB_BIN = "bb";
|
|
22
|
+
function toolEnv() {
|
|
23
|
+
const home = os.homedir();
|
|
24
|
+
const extraDirs = [path.join(home, ".nargo", "bin"), path.join(home, ".bb", "bin")];
|
|
25
|
+
const currentPath = process.env.PATH ?? "";
|
|
26
|
+
return {
|
|
27
|
+
...process.env,
|
|
28
|
+
PATH: [...extraDirs, currentPath].filter(Boolean).join(path.delimiter)
|
|
29
|
+
};
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
// src/graph.ts
|
|
33
|
+
var execFileAsync = promisify(execFile);
|
|
34
|
+
function edgeKey(from, to, ticket) {
|
|
35
|
+
return `${from}:${to}:${ticket}`;
|
|
36
|
+
}
|
|
37
|
+
function canonicalEdgeSet(edges, bidirectional) {
|
|
38
|
+
const set = /* @__PURE__ */ new Set();
|
|
39
|
+
for (const e of edges) {
|
|
40
|
+
set.add(edgeKey(e.from, e.to, e.ticket));
|
|
41
|
+
if (bidirectional) {
|
|
42
|
+
set.add(edgeKey(e.to, e.from, e.ticket));
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
return set;
|
|
46
|
+
}
|
|
47
|
+
var BoardGraph = class {
|
|
48
|
+
data;
|
|
49
|
+
graphToolsBin;
|
|
50
|
+
edges;
|
|
51
|
+
constructor(data, opts) {
|
|
52
|
+
this.data = data;
|
|
53
|
+
this.graphToolsBin = opts?.graphToolsBin ?? DEFAULT_GRAPH_TOOLS_BIN;
|
|
54
|
+
this.edges = canonicalEdgeSet(data.edges, data.bidirectional ?? true);
|
|
55
|
+
}
|
|
56
|
+
/** Pure, local check: is (from, to, ticket) a legal edge of this graph? */
|
|
57
|
+
hasEdge(from, to, ticket) {
|
|
58
|
+
return this.edges.has(edgeKey(from, to, ticket));
|
|
59
|
+
}
|
|
60
|
+
/** Edge-tree root (hex), via `zktable-graph root`. */
|
|
61
|
+
async root() {
|
|
62
|
+
const dir = await mkdtemp(path2.join(os2.tmpdir(), "zktable-graph-root-"));
|
|
63
|
+
try {
|
|
64
|
+
const graphPath = path2.join(dir, "graph.json");
|
|
65
|
+
await writeFile(graphPath, JSON.stringify(this.data));
|
|
66
|
+
const { stdout } = await execFileAsync(this.graphToolsBin, ["root", "--graph", graphPath], {
|
|
67
|
+
env: toolEnv()
|
|
68
|
+
});
|
|
69
|
+
return stdout.trim();
|
|
70
|
+
} finally {
|
|
71
|
+
await rm(dir, { recursive: true, force: true });
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
/** Poseidon2(node, salt) (hex), via `zktable-graph commit`. */
|
|
75
|
+
async commit(node, salt) {
|
|
76
|
+
const { stdout } = await execFileAsync(
|
|
77
|
+
this.graphToolsBin,
|
|
78
|
+
["commit", "--node", String(node), "--salt", salt.toString()],
|
|
79
|
+
{ env: toolEnv() }
|
|
80
|
+
);
|
|
81
|
+
return stdout.trim();
|
|
82
|
+
}
|
|
83
|
+
};
|
|
84
|
+
|
|
85
|
+
// src/prover.ts
|
|
86
|
+
import { execFile as execFile2 } from "child_process";
|
|
87
|
+
import { access, mkdtemp as mkdtemp2, readFile, rm as rm2, writeFile as writeFile2 } from "fs/promises";
|
|
88
|
+
import os3 from "os";
|
|
89
|
+
import path3 from "path";
|
|
90
|
+
import { promisify as promisify2 } from "util";
|
|
91
|
+
var execFileAsync2 = promisify2(execFile2);
|
|
92
|
+
async function exists(p) {
|
|
93
|
+
try {
|
|
94
|
+
await access(p);
|
|
95
|
+
return true;
|
|
96
|
+
} catch {
|
|
97
|
+
return false;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
var BoardProver = class {
|
|
101
|
+
circuitDir;
|
|
102
|
+
graphToolsBin;
|
|
103
|
+
nargoBin;
|
|
104
|
+
bbBin;
|
|
105
|
+
workDir;
|
|
106
|
+
env;
|
|
107
|
+
constructor(opts = {}) {
|
|
108
|
+
this.circuitDir = opts.circuitDir ?? DEFAULT_CIRCUIT_DIR;
|
|
109
|
+
this.graphToolsBin = opts.graphToolsBin ?? DEFAULT_GRAPH_TOOLS_BIN;
|
|
110
|
+
this.nargoBin = opts.nargoBin ?? DEFAULT_NARGO_BIN;
|
|
111
|
+
this.bbBin = opts.bbBin ?? DEFAULT_BB_BIN;
|
|
112
|
+
this.workDir = opts.workDir ?? os3.tmpdir();
|
|
113
|
+
this.env = toolEnv();
|
|
114
|
+
}
|
|
115
|
+
get targetDir() {
|
|
116
|
+
return path3.join(this.circuitDir, "target");
|
|
117
|
+
}
|
|
118
|
+
get bytecodePath() {
|
|
119
|
+
return path3.join(this.targetDir, `${CIRCUIT_PACKAGE_NAME}.json`);
|
|
120
|
+
}
|
|
121
|
+
get vkPath() {
|
|
122
|
+
return path3.join(this.targetDir, "vk");
|
|
123
|
+
}
|
|
124
|
+
/** Compile the circuit once if `target/move_along.json` is missing. */
|
|
125
|
+
async ensureCompiled() {
|
|
126
|
+
if (await exists(this.bytecodePath)) return;
|
|
127
|
+
await execFileAsync2(this.nargoBin, ["compile"], { cwd: this.circuitDir, env: this.env });
|
|
128
|
+
}
|
|
129
|
+
/** Generate the verification key once if `target/vk` is missing. */
|
|
130
|
+
async ensureVk() {
|
|
131
|
+
await this.ensureCompiled();
|
|
132
|
+
if (await exists(this.vkPath)) return;
|
|
133
|
+
await execFileAsync2(
|
|
134
|
+
this.bbBin,
|
|
135
|
+
[
|
|
136
|
+
"write_vk",
|
|
137
|
+
"--scheme",
|
|
138
|
+
"ultra_honk",
|
|
139
|
+
"--oracle_hash",
|
|
140
|
+
"keccak",
|
|
141
|
+
"--bytecode_path",
|
|
142
|
+
this.bytecodePath,
|
|
143
|
+
"--output_path",
|
|
144
|
+
this.targetDir,
|
|
145
|
+
"--output_format",
|
|
146
|
+
"bytes_and_fields"
|
|
147
|
+
],
|
|
148
|
+
{ env: this.env }
|
|
149
|
+
);
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Full pipeline: write graph -> `zktable-graph witness` -> `nargo execute`
|
|
153
|
+
* -> `bb prove`. Runs entirely inside an isolated temp dir; never touches
|
|
154
|
+
* `move_along/Prover.toml` or `move_along/target/`.
|
|
155
|
+
*/
|
|
156
|
+
async prove(graph, move) {
|
|
157
|
+
await this.ensureCompiled();
|
|
158
|
+
const dir = await mkdtemp2(path3.join(this.workDir, "zktable-prove-"));
|
|
159
|
+
try {
|
|
160
|
+
const graphPath = path3.join(dir, "graph.json");
|
|
161
|
+
const proverTomlPath = path3.join(dir, "Prover");
|
|
162
|
+
const witnessJsonPath = path3.join(dir, "witness.json");
|
|
163
|
+
const witnessOutPath = path3.join(dir, "witness");
|
|
164
|
+
await writeFile2(graphPath, JSON.stringify(graph));
|
|
165
|
+
await execFileAsync2(
|
|
166
|
+
this.graphToolsBin,
|
|
167
|
+
[
|
|
168
|
+
"witness",
|
|
169
|
+
"--graph",
|
|
170
|
+
graphPath,
|
|
171
|
+
"--from",
|
|
172
|
+
String(move.from),
|
|
173
|
+
"--to",
|
|
174
|
+
String(move.to),
|
|
175
|
+
"--ticket",
|
|
176
|
+
String(move.ticket),
|
|
177
|
+
"--salt-old",
|
|
178
|
+
move.saltOld.toString(),
|
|
179
|
+
"--salt-new",
|
|
180
|
+
move.saltNew.toString(),
|
|
181
|
+
"--prover",
|
|
182
|
+
`${proverTomlPath}.toml`,
|
|
183
|
+
"--json",
|
|
184
|
+
witnessJsonPath
|
|
185
|
+
],
|
|
186
|
+
{ env: this.env }
|
|
187
|
+
);
|
|
188
|
+
const witness = JSON.parse(await readFile(witnessJsonPath, "utf8"));
|
|
189
|
+
await execFileAsync2(this.nargoBin, ["execute", "--prover-name", proverTomlPath, witnessOutPath], {
|
|
190
|
+
cwd: this.circuitDir,
|
|
191
|
+
env: this.env
|
|
192
|
+
});
|
|
193
|
+
await execFileAsync2(
|
|
194
|
+
this.bbBin,
|
|
195
|
+
[
|
|
196
|
+
"prove",
|
|
197
|
+
"--scheme",
|
|
198
|
+
"ultra_honk",
|
|
199
|
+
"--oracle_hash",
|
|
200
|
+
"keccak",
|
|
201
|
+
"--bytecode_path",
|
|
202
|
+
this.bytecodePath,
|
|
203
|
+
"--witness_path",
|
|
204
|
+
`${witnessOutPath}.gz`,
|
|
205
|
+
"--output_path",
|
|
206
|
+
dir,
|
|
207
|
+
"--output_format",
|
|
208
|
+
"bytes_and_fields"
|
|
209
|
+
],
|
|
210
|
+
{ env: this.env }
|
|
211
|
+
);
|
|
212
|
+
const proof = new Uint8Array(await readFile(path3.join(dir, "proof")));
|
|
213
|
+
const publicInputs = new Uint8Array(await readFile(path3.join(dir, "public_inputs")));
|
|
214
|
+
return {
|
|
215
|
+
proof,
|
|
216
|
+
publicInputs,
|
|
217
|
+
cOld: witness.c_old,
|
|
218
|
+
cNew: witness.c_new,
|
|
219
|
+
root: witness.root,
|
|
220
|
+
ticket: move.ticket
|
|
221
|
+
};
|
|
222
|
+
} finally {
|
|
223
|
+
await rm2(dir, { recursive: true, force: true });
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
/** Off-chain check via `bb verify`. */
|
|
227
|
+
async verifyLocally(proof) {
|
|
228
|
+
await this.ensureVk();
|
|
229
|
+
const dir = await mkdtemp2(path3.join(this.workDir, "zktable-verify-"));
|
|
230
|
+
try {
|
|
231
|
+
const proofPath = path3.join(dir, "proof");
|
|
232
|
+
const publicInputsPath = path3.join(dir, "public_inputs");
|
|
233
|
+
await writeFile2(proofPath, proof.proof);
|
|
234
|
+
await writeFile2(publicInputsPath, proof.publicInputs);
|
|
235
|
+
try {
|
|
236
|
+
await execFileAsync2(
|
|
237
|
+
this.bbBin,
|
|
238
|
+
[
|
|
239
|
+
"verify",
|
|
240
|
+
"--scheme",
|
|
241
|
+
"ultra_honk",
|
|
242
|
+
"--oracle_hash",
|
|
243
|
+
"keccak",
|
|
244
|
+
"--proof_path",
|
|
245
|
+
proofPath,
|
|
246
|
+
"--vk_path",
|
|
247
|
+
this.vkPath,
|
|
248
|
+
"--public_inputs_path",
|
|
249
|
+
publicInputsPath
|
|
250
|
+
],
|
|
251
|
+
{ env: this.env }
|
|
252
|
+
);
|
|
253
|
+
return true;
|
|
254
|
+
} catch {
|
|
255
|
+
return false;
|
|
256
|
+
}
|
|
257
|
+
} finally {
|
|
258
|
+
await rm2(dir, { recursive: true, force: true });
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
};
|
|
262
|
+
export {
|
|
263
|
+
BoardGraph,
|
|
264
|
+
BoardProver
|
|
265
|
+
};
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
{
|
|
2
|
+
"nodes": [0, 1, 2, 3, 4, 5],
|
|
3
|
+
"bidirectional": true,
|
|
4
|
+
"edges": [
|
|
5
|
+
{ "from": 0, "to": 1, "ticket": 0 },
|
|
6
|
+
{ "from": 1, "to": 2, "ticket": 0 },
|
|
7
|
+
{ "from": 2, "to": 3, "ticket": 1 },
|
|
8
|
+
{ "from": 3, "to": 4, "ticket": 1 },
|
|
9
|
+
{ "from": 4, "to": 5, "ticket": 2 },
|
|
10
|
+
{ "from": 0, "to": 3, "ticket": 2 },
|
|
11
|
+
{ "from": 1, "to": 4, "ticket": 1 }
|
|
12
|
+
]
|
|
13
|
+
}
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
// zkTable `board` module - hidden movement on a public graph.
|
|
2
|
+
//
|
|
3
|
+
// Proves a piece moved from a hidden position to a new hidden position along a
|
|
4
|
+
// legal edge of a public transit graph, using an announced transport `ticket`,
|
|
5
|
+
// WITHOUT revealing either position.
|
|
6
|
+
//
|
|
7
|
+
// Commitments: C = Poseidon2(value, salt) (hash2)
|
|
8
|
+
// Edge leaf: L = Poseidon2(Poseidon2(from,to), ticket)
|
|
9
|
+
// Edge tree: a Merkle tree over all legal directed edges (from,to,ticket);
|
|
10
|
+
// its root `root` is a public per-map constant.
|
|
11
|
+
//
|
|
12
|
+
// hash2 == Barretenberg/Noir Poseidon2 over 2 inputs, which the off-chain tree
|
|
13
|
+
// builder (soroban-poseidon `poseidon2_hash`) reproduces exactly. Only hash2 is
|
|
14
|
+
// used so on-/off-chain hashing provably agree.
|
|
15
|
+
use dep::poseidon::poseidon2::Poseidon2;
|
|
16
|
+
|
|
17
|
+
// Merkle depth of the edge tree: 2^10 = 1024 directed edges (ample for a
|
|
18
|
+
// ~100-node map). Fixed so the circuit size is independent of map size.
|
|
19
|
+
global TREE_DEPTH: u32 = 10;
|
|
20
|
+
|
|
21
|
+
fn hash2(a: Field, b: Field) -> Field {
|
|
22
|
+
Poseidon2::hash([a, b], 2)
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
fn constrain_bit(bit: Field) {
|
|
26
|
+
assert(bit * (1 - bit) == 0);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
// Recompute a Merkle root from `leaf` and its authentication path.
|
|
30
|
+
// bit == 0 -> current node is the left child; bit == 1 -> right child.
|
|
31
|
+
fn compute_root(leaf: Field, siblings: [Field; TREE_DEPTH], bits: [Field; TREE_DEPTH]) -> Field {
|
|
32
|
+
let mut cur = leaf;
|
|
33
|
+
for i in 0..TREE_DEPTH {
|
|
34
|
+
let sib = siblings[i];
|
|
35
|
+
let bit = bits[i];
|
|
36
|
+
constrain_bit(bit);
|
|
37
|
+
if bit == 0 {
|
|
38
|
+
cur = hash2(cur, sib);
|
|
39
|
+
} else {
|
|
40
|
+
cur = hash2(sib, cur);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
cur
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
pub fn main(
|
|
47
|
+
c_old: pub Field,
|
|
48
|
+
c_new: pub Field,
|
|
49
|
+
ticket: pub Field,
|
|
50
|
+
root: pub Field,
|
|
51
|
+
from: Field,
|
|
52
|
+
salt_old: Field,
|
|
53
|
+
to: Field,
|
|
54
|
+
salt_new: Field,
|
|
55
|
+
path_siblings: [Field; TREE_DEPTH],
|
|
56
|
+
path_bits: [Field; TREE_DEPTH],
|
|
57
|
+
) {
|
|
58
|
+
// 1. The hidden old position matches the committed current position.
|
|
59
|
+
assert(hash2(from, salt_old) == c_old);
|
|
60
|
+
// 2. The hidden new position matches the announced new commitment.
|
|
61
|
+
assert(hash2(to, salt_new) == c_new);
|
|
62
|
+
// 3. (from, to, ticket) is a legal edge: its leaf is in the edge tree.
|
|
63
|
+
let leaf = hash2(hash2(from, to), ticket);
|
|
64
|
+
assert(compute_root(leaf, path_siblings, path_bits) == root);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
#[test]
|
|
68
|
+
fn test_smoke() {
|
|
69
|
+
// Sanity: a commitment round-trips. (Full membership is exercised by the
|
|
70
|
+
// Rust witness builder + on-chain tests, which control the tree root.)
|
|
71
|
+
let c = hash2(7, 42);
|
|
72
|
+
assert(c == hash2(7, 42));
|
|
73
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"noir_version":"1.0.0-beta.9+6abff2f16e1c1314ba30708d1cf032a536de3d19","hash":"6959141722380247666","abi":{"parameters":[{"name":"c_old","type":{"kind":"field"},"visibility":"public"},{"name":"c_new","type":{"kind":"field"},"visibility":"public"},{"name":"ticket","type":{"kind":"field"},"visibility":"public"},{"name":"root","type":{"kind":"field"},"visibility":"public"},{"name":"from","type":{"kind":"field"},"visibility":"private"},{"name":"salt_old","type":{"kind":"field"},"visibility":"private"},{"name":"to","type":{"kind":"field"},"visibility":"private"},{"name":"salt_new","type":{"kind":"field"},"visibility":"private"},{"name":"path_siblings","type":{"kind":"array","length":10,"type":{"kind":"field"}},"visibility":"private"},{"name":"path_bits","type":{"kind":"array","length":10,"type":{"kind":"field"}},"visibility":"private"}],"return_type":null,"error_types":{}},"bytecode":"H4sIAAAAAAAA/9VcCVNbZRS9CXZzrZCwtlWrVkUteVkgoS6glrqAWuoCaqlFgpa6gFrqAmqpC6ilLqCWuoD6Ox3vLd/nXEM68005t/PyZs7kNbSn596TnAMheQlaP/5mDNHGI+Fue9xtLtOZz5e7suUoFx3PZEujxUImXxjtLEbFqFAsjGWLuVy5mC92lUZLXZlSlM+Vo/FCKTeeWT92Ka7MJg9LnbuvXGe28g7RVs+4RmmV83/c+RZ1vkud73bn/t/tYdzCuJVxm7rfH0nwDgjnVbQH6Hu1fW5Ve9sWuM+9jNsZdzDuvAr7TAD3udd4n/rxuTVwn/sYdzHuZtzj7q/GvU9xJAO52xn3Mu5j3F/Bh/So3umt5M1s7ojqgX5Vzq6POOvWevdbCt5vwNtB2GC1mLtDLRjEWzUc5Mnon6jbKewJLENHjKzsjy4fDpqvPZA7zygwOhld6n50gLe7HaM863B7SWI9i9qBMxcJ+w0bOrAbmKOB8M+nBqrNwEbq1npLloJLBrzdFO/Alrm71YJBvJe0ooNPgipP2OArEj748sCZD5BtiQq/L7QdFFZ0DzAeZDzEeJjsiq7b6UP50u20o/0+AJy5x9hv7XFPoN+9jEcYjzIeI7ufelLMkSJ8xqWoNksUqVvrPWgp+KABbx/Fu0Rl7j61YBBv1RLNbO747xsS1D6Fr9dAZy9Q4yGyDVXh9+F5LYWF6uOMJxhPMp4iuxLtc/pQvvQ57Wi/DwFn7jf2W3vcH+j3AONpxjOMZ8muRNPMkSZ8xqWpNksUqVvrPWwp+LAB7yDFu0Rl7kG1YBCvSYlKCPYTNqQHDHQOADUeIdtQFX4fntdRWKg+x3ie8QLjRbIr0UGnD+XLoNOO9vsIcOYhY7+1x0OBfg8zXmK8zHiF7Eq0kTkaCZ9xjVSbJYrUrfUetRR81IB3hOJdojL3iFowiNekRCUEhwgb0sMGOoeBGo+RbagKvw/P6yksVF9lHGeMMl4juxIdcfpQvow47Wi/jwFnHjP2W3s8Fuh3mTHOeJ3xBtmVaBNzNBE+45qoNksUqVvrPWEp+IQB7wTFu0Rl7gm1YBCvSYlKCI4RNqTLBjrLQI0nyTZUhd+H5w0UFqpvMt5ivM14h+xKdMLpQ/ky4bSj/T4JnHnS2G/t8WSg31OMdxnvMd4nuxJtZo5mwmdcM9VmiSJ1a72nLAWfMuCdpniXqMw9rRYM4jUpUQnBScKG9JSBzimgxtNkG6rC78PzRgoL1Q8YHzI+YnxMdiU67fShfJl22tF+nwbOPGPst/Z4JtDvWcYnjE8Zn5FdibYwRwvhM66FarNEkbq13jOWgs8Y8M5RvEtU5p5TCwbxmpSohOAMYUN61kDnLFDjWbINVeH34XkThYXq54wvGF8yviK7Ep1z+lC+zDntaL/PAmeeN/Zbezwf6PcC42vGN4xvya5EW5mjlfAZ10q1WaJI3VrvOUvB5wx4FyneJSpzL6oFg3hNSlRCcJ6wIb1goHMBqPE82Yaq8Pvw3Elhofod43vGD4wfya5EF50+lC+LTjva7/PAmZeM/dYeLwX6vcz4ifEz4xeyK9E25mgjfMa1UW2WKFK31nvBUvAFA94VineJytwrasEgXpMSlRBcImxILxvoXAZqvEi2oSr8PjxvprBQ/ZXxG+N3xh9kV6IrTh/KlxWnHe33ReDMq8Z+a49XA/1eY/zJ+IvWr+R1Ob8zmzsu+bMKfvysGTwu64AzrxHWb+9Ns7uVP8sVwOQqS3LlKrkAinxWWD7qJO/Uljeaye/J5WV+eZVip3uMyONGriEgH4GUT3DIG1CbHK+8eik/fLXR/69qlXC7rqONh++tHRW3afV15F49f8qGP7OtyoxpdZ6qmDOpvtYD0uD5/L630MYjWfE1/3e3V+hL4PVFlVrqqvxf/mhwtyl1n9/nvxLJZr5GUAAA","debug_symbols":"vVjtbqMwEHwXfvPD6/X6417ldKpoSiskRCKaVDpVffczYSDtSUYRe70/mSRmRrvjYS14r57ax8vLQzc8H1+rHz/fq8ex6/vu5aE/Hppzdxzyv+8fdbX8fDiPbZv/qj6tZ9apGdvhXP0YLn1fV29Nf7le9HpqhiuemzGvmrpqh6eMWfC569vp20d9Y5sy1RoKYFvDcRWQrwpUViBjExTIiJQUbFmBxUKAU7jx4xc+b/RgiZcerPUlBbfRA7lFgcj7XTUEs9YQXUnBb9QQxC01hMAlhVBWSNZDIHHawSdjVheM83t6iGlxgZIp9nBvHl0opWlLgVgWBRJXTLRVR5pYmWly6lCTqFO9XcVdsaagzjVFZbC3BO5M9mYb+mh/DqbnPdG2Xm67YYqjlvXT2imjbUUdKqsfllY7La1+XNrvnZdW0s3LVNpP1h/grD7B9Uc4/4MzXH+Isz6YrA0m64PJ3xtMXouwXD7I3VYwnYtLEU7SPom49uHizirSWoWQL0psRpPsGk1K+ySMrBLW6CVklxfCq51SflrYlvA3iVCuIqkHlhjlwBJSjwqx6lEhrBwVwupRsdnGfaNiMxOeVie8Ld4fEvSZiNpMJP0zoFFnwpMyE570j4Hmvx0ff+3nr/yrOXTjl3cplckN1xVdP+31k6dBV1duepSsK5l2pa58hrwWpl2uq5iDmVOVMuRkkAESMOtInpmUlXwuh9ycIJKZRh7XBWAEpplnDZBmvrVAnvnWzddbAULPBvAiMM08NkCa+Wzn65mB0GOZeeyBAbwITDPfoV+Hfh30HM8854Ay85wHBvDRr4N/Aj2hmSfwT+CfOCD8E/Qr8E+gJ/DPwz8P/zz88/DPo18P/zz0PPzz8M/DvwD/AvwL6DfAvwC9AP8C/AvwL8C/AP8i+o3wL0Ivwr8I/yL8i/AvTnpTpt+asWse+xYvA58vw+HTu8Hz79Oysrw9PI3HQ/t0Gdsp+9e1fDf8AQ==","file_map":{"50":{"source":"// zkTable `board` module - hidden movement on a public graph.\r\n//\r\n// Proves a piece moved from a hidden position to a new hidden position along a\r\n// legal edge of a public transit graph, using an announced transport `ticket`,\r\n// WITHOUT revealing either position.\r\n//\r\n// Commitments: C = Poseidon2(value, salt) (hash2)\r\n// Edge leaf: L = Poseidon2(Poseidon2(from,to), ticket)\r\n// Edge tree: a Merkle tree over all legal directed edges (from,to,ticket);\r\n// its root `root` is a public per-map constant.\r\n//\r\n// hash2 == Barretenberg/Noir Poseidon2 over 2 inputs, which the off-chain tree\r\n// builder (soroban-poseidon `poseidon2_hash`) reproduces exactly. Only hash2 is\r\n// used so on-/off-chain hashing provably agree.\r\nuse dep::poseidon::poseidon2::Poseidon2;\r\n\r\n// Merkle depth of the edge tree: 2^10 = 1024 directed edges (ample for a\r\n// ~100-node map). Fixed so the circuit size is independent of map size.\r\nglobal TREE_DEPTH: u32 = 10;\r\n\r\nfn hash2(a: Field, b: Field) -> Field {\r\n Poseidon2::hash([a, b], 2)\r\n}\r\n\r\nfn constrain_bit(bit: Field) {\r\n assert(bit * (1 - bit) == 0);\r\n}\r\n\r\n// Recompute a Merkle root from `leaf` and its authentication path.\r\n// bit == 0 -> current node is the left child; bit == 1 -> right child.\r\nfn compute_root(leaf: Field, siblings: [Field; TREE_DEPTH], bits: [Field; TREE_DEPTH]) -> Field {\r\n let mut cur = leaf;\r\n for i in 0..TREE_DEPTH {\r\n let sib = siblings[i];\r\n let bit = bits[i];\r\n constrain_bit(bit);\r\n if bit == 0 {\r\n cur = hash2(cur, sib);\r\n } else {\r\n cur = hash2(sib, cur);\r\n }\r\n }\r\n cur\r\n}\r\n\r\npub fn main(\r\n c_old: pub Field,\r\n c_new: pub Field,\r\n ticket: pub Field,\r\n root: pub Field,\r\n from: Field,\r\n salt_old: Field,\r\n to: Field,\r\n salt_new: Field,\r\n path_siblings: [Field; TREE_DEPTH],\r\n path_bits: [Field; TREE_DEPTH],\r\n) {\r\n // 1. The hidden old position matches the committed current position.\r\n assert(hash2(from, salt_old) == c_old);\r\n // 2. The hidden new position matches the announced new commitment.\r\n assert(hash2(to, salt_new) == c_new);\r\n // 3. (from, to, ticket) is a legal edge: its leaf is in the edge tree.\r\n let leaf = hash2(hash2(from, to), ticket);\r\n assert(compute_root(leaf, path_siblings, path_bits) == root);\r\n}\r\n\r\n#[test]\r\nfn test_smoke() {\r\n // Sanity: a commitment round-trips. (Full membership is exercised by the\r\n // Rust witness builder + on-chain tests, which control the tree root.)\r\n let c = hash2(7, 42);\r\n assert(c == hash2(7, 42));\r\n}\r\n","path":"/mnt/c/Users/freed/OneDrive/Desktop/zkTable/packages/circuits/move_along/src/main.nr"},"58":{"source":"use std::default::Default;\nuse std::hash::Hasher;\n\ncomptime global RATE: u32 = 3;\n\npub struct Poseidon2 {\n cache: [Field; 3],\n state: [Field; 4],\n cache_size: u32,\n squeeze_mode: bool, // 0 => absorb, 1 => squeeze\n}\n\nimpl Poseidon2 {\n #[no_predicates]\n pub fn hash<let N: u32>(input: [Field; N], message_size: u32) -> Field {\n Poseidon2::hash_internal(input, message_size)\n }\n\n pub(crate) fn new(iv: Field) -> Poseidon2 {\n let mut result =\n Poseidon2 { cache: [0; 3], state: [0; 4], cache_size: 0, squeeze_mode: false };\n result.state[RATE] = iv;\n result\n }\n\n fn perform_duplex(&mut self) {\n // add the cache into sponge state\n for i in 0..RATE {\n // We effectively zero-pad the cache by only adding to the state\n // cache that is less than the specified `cache_size`\n if i < self.cache_size {\n self.state[i] += self.cache[i];\n }\n }\n self.state = crate::poseidon2_permutation(self.state, 4);\n }\n\n fn absorb(&mut self, input: Field) {\n assert(!self.squeeze_mode);\n if self.cache_size == RATE {\n // If we're absorbing, and the cache is full, apply the sponge permutation to compress the cache\n self.perform_duplex();\n self.cache[0] = input;\n self.cache_size = 1;\n } else {\n // If we're absorbing, and the cache is not full, add the input into the cache\n self.cache[self.cache_size] = input;\n self.cache_size += 1;\n }\n }\n\n fn squeeze(&mut self) -> Field {\n assert(!self.squeeze_mode);\n // If we're in absorb mode, apply sponge permutation to compress the cache.\n self.perform_duplex();\n self.squeeze_mode = true;\n\n // Pop one item off the top of the permutation and return it.\n self.state[0]\n }\n\n fn hash_internal<let N: u32>(input: [Field; N], in_len: u32) -> Field {\n let two_pow_64 = 18446744073709551616;\n let iv: Field = (in_len as Field) * two_pow_64;\n let mut sponge = Poseidon2::new(iv);\n for i in 0..input.len() {\n if i < in_len {\n sponge.absorb(input[i]);\n }\n }\n sponge.squeeze()\n }\n}\n\npub struct Poseidon2Hasher {\n _state: [Field],\n}\n\nimpl Hasher for Poseidon2Hasher {\n fn finish(self) -> Field {\n let iv: Field = (self._state.len() as Field) * 18446744073709551616; // iv = (self._state.len() << 64)\n let mut sponge = Poseidon2::new(iv);\n for i in 0..self._state.len() {\n sponge.absorb(self._state[i]);\n }\n sponge.squeeze()\n }\n\n fn write(&mut self, input: Field) {\n self._state = self._state.push_back(input);\n }\n}\n\nimpl Default for Poseidon2Hasher {\n fn default() -> Self {\n Poseidon2Hasher { _state: &[] }\n }\n}\n","path":"/home/freed/nargo/github.com/noir-lang/poseidon/v0.2.0/src/poseidon2.nr"}},"names":["main"],"brillig_names":["directive_invert"]}
|
|
Binary file
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
["0x0000000000000000000000000000000000000000000000000000000000002000","0x0000000000000000000000000000000000000000000000000000000000000014","0x0000000000000000000000000000000000000000000000000000000000000001","0x00000000000000000000000000000000000000000000000000000000ffffffff","0x0000000000000000000000000000001ef05de4597e054159db57dd7470a2b402","0x0000000000000000000000000000000000139ab1aebf70f7e418006c183311d3","0x00000000000000000000000000000026dec106813aaa74653647525320f29882","0x000000000000000000000000000000000009239bcef4364c3574d6ef26a3bfe6","0x00000000000000000000000000000057adbd851607ee1ed5ea1a41b0c78bd44f","0x000000000000000000000000000000000023c1e865bc75235d501d32fd4f4fa2","0x000000000000000000000000000000a979f9f657a5c4721a7171f24639d0697f","0x00000000000000000000000000000000000e785e558f50f0142e56801052e410","0x000000000000000000000000000000e23edea058f9898ec8357e3b9e5c00b39c","0x0000000000000000000000000000000000076f57e17f022f69dd396da533a107","0x0000000000000000000000000000009719b77ae55119c350544fb988f82136b5","0x0000000000000000000000000000000000146d8e33ec2112d2bd44d9fa1cf485","0x000000000000000000000000000000500f0c2ae144841772c6e0e4d2e546964f","0x000000000000000000000000000000000009728566bf6c0fca86f2fe9c04cb97","0x0000000000000000000000000000002d47c8e9b3c015247f287e1e4092696b32","0x00000000000000000000000000000000000a0333e42b7f3e7b2af908784cdea3","0x000000000000000000000000000000543191359812971f18d81711b65326304c","0x00000000000000000000000000000000002a610f2dea6754384d67544c5e504f","0x0000000000000000000000000000000c83301ab472d78da737dd849ec7e01e47","0x000000000000000000000000000000000029ca545a081a8cba846a0b27b48b90","0x000000000000000000000000000000aa61ce8c9d39cd8464460c6c4871d3c10a","0x0000000000000000000000000000000000303709216a00f9c239a25d7fa5cffe","0x0000000000000000000000000000007b17dc13b22c19dd53a3b4772a38787da7","0x0000000000000000000000000000000000216b948d742e31108609006235dd22","0x0000000000000000000000000000002afc5cac5dabeb8f74a2f89ad33f068fe4","0x0000000000000000000000000000000000038147f7985ab2a8d179a7a764ee62","0x0000000000000000000000000000005c7f68b34721dbdaa9d8f2cfc9f432da95","0x000000000000000000000000000000000024095afc77887b20f8293c4a2602c5","0x00000000000000000000000000000024e640d77486f241df4e65111ec10d14f5","0x00000000000000000000000000000000000280de4001cdd14d69feefc78a0bde","0x000000000000000000000000000000fd9384ac9af95c9c63dc68d6910b0710a5","0x00000000000000000000000000000000000ce10088560e20ee658cb12307ed00","0x0000000000000000000000000000005d99df2137d3e4acb3ca67496281caf8cd","0x0000000000000000000000000000000000199f4330b5979787d8e5016f3e05ad","0x0000000000000000000000000000001402447eb36518626878b6db427325cd93","0x00000000000000000000000000000000000d5fbeae433d2437797c7b6b83252a","0x0000000000000000000000000000006623c6b5d1a214e18ced1876f58c287408","0x0000000000000000000000000000000000299c621029e110ef289b105aa23259","0x00000000000000000000000000000029ad608e8c57a845f6b206a7cd06f20dc9","0x00000000000000000000000000000000001afdd25d347f91346774ed90a67adb","0x000000000000000000000000000000d0636acabe42d9b0f674cdca99e8f44108","0x000000000000000000000000000000000029ebcaefa30abd527532dcc66013e6","0x0000000000000000000000000000006b0fa0d80de336b42b45264bef3f198065","0x000000000000000000000000000000000026c71671e8bcfb09be9b289db68b46","0x0000000000000000000000000000009aa7b8224af28a2c7ea03cc9db08453fd1","0x0000000000000000000000000000000000205ca51860ff55aa8cf144a856e27b","0x000000000000000000000000000000f678538b6c4b97cbe84f0a1c2d7e7c9b5b","0x000000000000000000000000000000000013cca1be27d3214dab1dbf8c4fd3cb","0x000000000000000000000000000000eb30e1649e76e0d2bc69a5bebcaecac477","0x000000000000000000000000000000000024f2816a22f43bfa20898b00903c63","0x000000000000000000000000000000cea31fa01d6812eeee1998b49bb4cd2d27","0x000000000000000000000000000000000003e81da072f839c554aec2c67d6d44","0x0000000000000000000000000000002179fe8a3e0d08d7ff0b0bc34e27a1ca99","0x00000000000000000000000000000000001339e8e774420af78a74d890d51b55","0x000000000000000000000000000000d77357ff968dff59cdf9cfc611c4a94de0","0x0000000000000000000000000000000000087e076ff6fd82bc8541c7cee2a585","0x00000000000000000000000000000049dc2c7d4cbd887a66c12d0df2ad642bd5","0x000000000000000000000000000000000014b096d6d772838b9057f96d9a91f6","0x0000000000000000000000000000008639fb5d137c3d1533ef479e2ea8a394d2","0x00000000000000000000000000000000001b112d95e3bf5ab6e289ae96d2a32f","0x000000000000000000000000000000cf05ea277117ba0a5e68ceb5925f4ff19d","0x00000000000000000000000000000000001aa3a6515cb0b178ea8120bab41ef4","0x00000000000000000000000000000048c56751c923baee6e6fd32516d6e42ef6","0x000000000000000000000000000000000027b8d4b65b7270977ce60c3e419a9b","0x000000000000000000000000000000d5b1671bde7f611362adbb2d0c4624d5a7","0x0000000000000000000000000000000000130af9926885bd8fd5d9c2c184bfca","0x000000000000000000000000000000c66f6698adb195f66d55a03f6305b7a024","0x0000000000000000000000000000000000035d11ee534c68b9bcf90825df832c","0x0000000000000000000000000000009069432b2a69f3041306d48ec527c9cefd","0x00000000000000000000000000000000000d07332edd7aacb652b5411cef2982","0x00000000000000000000000000000076f8db0e1face5fd0f67f8d4c2c28e315e","0x000000000000000000000000000000000003358d6d5e694120bd0d7566bdd5e8","0x0000000000000000000000000000008a9bfd223934448ddba868c79c656693bf","0x000000000000000000000000000000000012387ccaa191748f4cda25aeb64600","0x000000000000000000000000000000713eefc86849a12bca1617dd808a1bad85","0x000000000000000000000000000000000028cc75d56bd3f1683ae3d47c2d3888","0x0000000000000000000000000000007356c3ec724b3d2991f524eefa9a3bbd68","0x00000000000000000000000000000000001c3082cde00068be5035920b023a4b","0x000000000000000000000000000000a221c31386db5eee28d9c35bc79a45e5c3","0x00000000000000000000000000000000001fe33f8d98e4d98368e110874eb40b","0x0000000000000000000000000000001421e83c871747e7223f12276091f94c41","0x00000000000000000000000000000000001a33cf3755a386aabba274a397ecc7","0x000000000000000000000000000000eda4b997a3c65ef6e48f404dfa8628e206","0x000000000000000000000000000000000000b633ed858b8e6554aba494c3f262","0x0000000000000000000000000000003cee056cd8653f11fe91bec67f9a1ba501","0x00000000000000000000000000000000000cb15289361c0a0e1b78f25efb7e6f","0x000000000000000000000000000000443f54f12a87c2cf5182f3620fc1944c6d","0x000000000000000000000000000000000029664df9e7f07b4aec2f396f6cde12","0x00000000000000000000000000000073875103abf917a76019cf7bba4da77621","0x0000000000000000000000000000000000070b433d46367e191b9bf40eef28b6","0x000000000000000000000000000000a0af4c7b9ef86fe2480692f5f6dc52534a","0x000000000000000000000000000000000026eccd7100479fc88688e129589197","0x0000000000000000000000000000009fb1952dd9aeab56e182d68b662852e36a","0x00000000000000000000000000000000001d62dc541680650e594af57d090320","0x0000000000000000000000000000008dff03113bc84bd8a1582702c3a51cc8fd","0x0000000000000000000000000000000000150131f285f1648db0d2d85128255b","0x0000000000000000000000000000006f575a60d3c9d50fc277988d94997a5ddb","0x00000000000000000000000000000000000082e0b52e8df94612b14bc2afb9f7","0x000000000000000000000000000000fe073ff12f2bad78b10ae4a1629516a075","0x000000000000000000000000000000000026a696f75adf15d5934d9edad81c9b","0x0000000000000000000000000000000000000000000000000000000000000001","0x0000000000000000000000000000000000000000000000000000000000000000","0x0000000000000000000000000000000000000000000000000000000000000002","0x0000000000000000000000000000000000000000000000000000000000000000","0x0000000000000000000000000000006e1f2f143b82ea9ac5ecfb71b5fbfe4324","0x0000000000000000000000000000000000037f638c9ab695c3fc340ab91c29ea","0x00000000000000000000000000000084bec3c120d398b8b73c31448b7511d13a","0x0000000000000000000000000000000000213eef8b9f689e4cc1c06dd04cd5f1"]
|
package/package.json
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@zktable/circuits",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Pre-built Noir (UltraHonk) circuits + witness builders for zkTable modules",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"repository": {
|
|
8
|
+
"type": "git",
|
|
9
|
+
"url": "git+https://github.com/Philotheephilix/zkTable.git",
|
|
10
|
+
"directory": "packages/circuits"
|
|
11
|
+
},
|
|
12
|
+
"publishConfig": {
|
|
13
|
+
"access": "public"
|
|
14
|
+
},
|
|
15
|
+
"main": "./dist/index.cjs",
|
|
16
|
+
"module": "./dist/index.js",
|
|
17
|
+
"types": "./dist/index.d.ts",
|
|
18
|
+
"exports": {
|
|
19
|
+
".": {
|
|
20
|
+
"import": "./dist/index.js",
|
|
21
|
+
"require": "./dist/index.cjs",
|
|
22
|
+
"types": "./dist/index.d.ts"
|
|
23
|
+
}
|
|
24
|
+
},
|
|
25
|
+
"files": [
|
|
26
|
+
"dist",
|
|
27
|
+
"move_along",
|
|
28
|
+
"dice_valid",
|
|
29
|
+
"card_membership",
|
|
30
|
+
"scripts",
|
|
31
|
+
"README.md"
|
|
32
|
+
],
|
|
33
|
+
"engines": {
|
|
34
|
+
"node": ">=20"
|
|
35
|
+
},
|
|
36
|
+
"scripts": {
|
|
37
|
+
"build:circuits": "bash scripts/build_all.sh",
|
|
38
|
+
"build": "tsup src/index.ts --format esm,cjs --dts",
|
|
39
|
+
"test": "vitest run",
|
|
40
|
+
"typecheck": "tsc --noEmit"
|
|
41
|
+
}
|
|
42
|
+
}
|