SkateSpots/scripts/cordn-benchmark.ts

81 lines
2.7 KiB
TypeScript

/**
* Live Cordn native benchmark — send/decrypt/state-size on the real coordinator.
*
* npx tsx scripts/cordn-benchmark.ts
* CORDN_BENCH_N=50 npx tsx scripts/cordn-benchmark.ts
*
* Creates a throwaway two-member group, warms up, measures N encrypted sends
* and N decrypting fetches, and reports the persisted snapshot size (the same
* shape IndexedDB stores). No user data or secrets are logged.
*/
import { performance } from 'node:perf_hooks';
import { CordnSession, MemoryCordnStore, type CordnSnapshot, type CordnStore } from '../src/lib/cordn/native/session';
const N = Math.max(5, Math.min(Number(process.env.CORDN_BENCH_N ?? 30), 100));
const coordinator = {
serverPubkey: '02816a05b1d4e70a7df9c712ef6f7272774269d65bd8a2f262ce0330d0885693',
relays: ['wss://relay.skate-spots.org'],
};
class MeasuringStore implements CordnStore {
private inner = new MemoryCordnStore();
lastBytes = 0;
async load(): Promise<CordnSnapshot | null> {
return this.inner.load();
}
async save(snapshot: CordnSnapshot): Promise<void> {
this.lastBytes = JSON.stringify(snapshot).length;
await this.inner.save(snapshot);
}
async clear(): Promise<void> {
await this.inner.clear();
}
}
const aStore = new MeasuringStore();
const bStore = new MeasuringStore();
const a = await CordnSession.open({ coordinator, store: aStore });
const b = await CordnSession.open({ coordinator, store: bStore });
await a.generateKeyPackage('a');
const bk = await b.generateKeyPackage('b');
await a.publishKeyPackage('a');
await b.publishKeyPackage('b');
const gid = `bench-${Date.now()}`;
const group = await a.createGroup({ groupId: gid, name: 'Benchmark' });
const { welcomeBase64 } = await a.addMember(group.gid, bk.keyPackage);
const bGroup = await b.joinGroup({ welcomeBase64, keyPackage: bk, name: 'Benchmark' });
for (let i = 0; i < 3; i += 1) {
await a.send(gid, `warmup ${i}`);
await b.fetch(gid);
}
const sendStart = performance.now();
for (let i = 0; i < N; i += 1) await a.send(gid, `bench message ${i}`);
const sendMs = performance.now() - sendStart;
const fetchStart = performance.now();
const received = await b.fetch(bGroup.gid);
const fetchMs = performance.now() - fetchStart;
const sendPer = sendMs / N;
const fetchPer = fetchMs / N;
console.log(
JSON.stringify(
{
messages: N,
sendMs: Math.round(sendMs),
sendPerMessageMs: Math.round(sendPer * 10) / 10,
fetchMs: Math.round(fetchMs),
fetchPerMessageMs: Math.round(fetchPer * 10) / 10,
received: received.length,
snapshotBytesA: aStore.lastBytes,
snapshotBytesB: bStore.lastBytes,
note: 'Memory snapshot shape matches the IndexedDB adapter; network + coordinator included.',
},
null,
2,
),
);
await a.disconnect();
await b.disconnect();