Inspiration
My brother and teammate receives services at an opioid drop-in center like the one where I work as a Peer Lead, serving roughly 15,000 contacts a year. He's watched people walk in straight from prison or institutions and freeze — long lines, strangers, staff taking 42 CFR Part 2 information on paper while typing de-identified numbers into Excel. In that line, asking for help means being seen, and being seen has a cost. We built Midnight ID so proving you belong takes seconds and reveals nothing.
What it does
Organizations enroll participants by placing only a cryptographic commitment on-chain — the person's alias never leaves the org's device. Participants check in with a zero-knowledge Merkle membership proof; a daily nullifier blocks double check-ins without linking any check-in to an identity. Any third organization — housing, employment — can verify someone holds a valid credential while learning nothing else. The public ledger sees only proofs, hashes, and counts.
How we built it
Three Compact circuits (enroll, checkIn, verifyCredential) on a HistoricMerkleTree with domain-separated commitment and nullifier hashes, compiled with compactc 0.31.0. TypeScript witnesses and a contract simulator with 8/8 tests passing — success and failure cases for every circuit. A Node demo server runs the compiled circuits and plays the role of the org's local device; a React UI shows the three panels plus a live "what the chain sees" strip.
Challenges we ran into
The Compact compiler's disclosure rules taught us exactly where witness data could leak — every fix made the privacy model sharper. The browser couldn't run the proof runtime directly, so we moved circuit execution to a Node server, which ended up mirroring the correct production architecture: operational data on the org's device, only the proof layer on-chain.
Accomplishments that we're proud of
A complete working loop — enroll, check in, double-check-in rejection, third-party verification — running real compiled circuits, built and tested in one weekend. And a demo where the privacy guarantee is visible on screen: names above the line, only hashes below it.
What we learned
Zero-knowledge design is about deciding what NOT to prove — our verify circuit deliberately proves membership, not attendance, because attendance counts would require exactly the linkability the design forbids.
What's next for Midnight ID
Admin-gated enrollment, milestone credentials (prove N or more check-ins without revealing which), and Preprod deployment — the provider plumbing is already retained in the repo.
Built With
- compact
- midnight
- node.js
- react
- typescript
- vite
Log in or sign up for Devpost to join the conversation.