Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Why Compact?

This note explains why Compact exists, the problem it solves, why traditional approaches fail, and what design choices make it different.


Intuition First

Before Compact, writing privacy-preserving smart contracts required either:

  1. Writing raw ZK circuits, Cryptographically correct but inaccessible to most developers.
  2. Using traditional smart contracts, Accessible but with no privacy at all.

Compact sits between these extremes. It makes privacy-preserving computation accessible to TypeScript developers by handling the circuit generation automatically. You write code that looks familiar; the compiler produces the cryptographic machinery.

The tradeoff is bounded computation. Compact intentionally cannot express Turing-complete programs. In exchange, every valid program compiles to a circuit.


The Three Approaches

ApproachPrivacyAccessibilityComplexity
Raw ZK circuitsFullRequires cryptographic expertiseExtremely high
Traditional smart contracts (Solidity)NoneAccessible to developersLow
CompactFullTypeScript-like syntaxMedium

Compact doesn’t add privacy to existing contracts. It builds privacy into the model from the start, at the language level.


The Privacy Model

Traditional smart contracts have one world: public state that everyone can see. Midnight has two.

WorldLocationVisibilityContents
PublicOn-chainEveryoneProofs, contract code, public data
PrivateLocal storageOnly the ownerSensitive data, secrets

Computations happen locally on private data. A ZK proof of correctness is submitted on-chain. Validators verify the proof without seeing the inputs.

The key insight: Privacy doesn’t mean “hiding everything.” It means proving you have the right to do something without revealing what that something is. A ZK proof says: “I ran this computation correctly” without revealing the inputs to that computation.


Why Not Just Use Traditional Contracts?

Traditional contracts make everything public by default. This is fine for many use cases, but breaks down when:

  • Regulated data, Healthcare (HIPAA), finance (SOX), identity (KYC). Public exposure isn’t optional.
  • Competitive data, Bid amounts, inventory levels, proprietary information.
  • Personal data, Balances, transaction history, credit scores.

You could encrypt data on-chain, but then no one can verify computation on it. Traditional ZK approach is to write circuits from scratch, extremely difficult to get right and audit.

Compact makes the ZK approach accessible.


Type Safety at the Language Level

LanguageType SafetyWhat it means
JavaScriptNoneAny value, any type, runtime errors
SolidityLoosely typedImplicit conversions, overflow allowed
TypeScriptOptionalOpt-in with tsconfig, can be bypassed
CompactStrong, enforcedCompiler rejects any program that doesn’t type-check

Strong type safety matters in Compact because the type system tracks data flow for privacy enforcement. If types were loose, the compiler couldn’t track where private data travels.


Verifiability vs. Privacy

| You want | Traditional contracts | Raw ZK circuits | Compact | |———|—————––|—————–|—————|––––| | Everything verifiable | Yes | Yes | Yes | | Full privacy | No | Yes | Yes | | Accessible syntax | Yes | No | Yes |

Compact gives you both verifiability and privacy without requiring cryptographic expertise. You don’t write a single circuit by hand.


Selective Disclosure

Compact supports selective disclosure, users choose exactly what to reveal and to whom. This enables regulated use cases:

  • Healthcare: Prove you meet age requirements without revealing your birthday.
  • Finance: Prove your balance exceeds a threshold without revealing the balance.
  • Identity: Prove citizenship without revealing your nationality or full address.

This isn’t a feature bolted on. It’s baked into the model via disclose(), a compile-time boundary that marks intentional disclosure.


When to Choose Compact

Use Compact when you need:

  • Privacy-preserving logic on a public blockchain
  • To prove correctness without revealing inputs
  • TypeScript-like development without learning ZK circuit design
  • Selective disclosure for regulated data

When Not to Choose Compact

Compact is not the right tool when:

ScenarioWhy not CompactAlternative
No privacy requirementsTraditional contracts are simplerSolidity
Turing-complete computation neededCompact is intentionally boundedRaw circuits
Dynamically-sized data structuresAll sizes must be compile-time constantsDesign around bounded structures
Complex cryptography neededCompact generates standard circuitsWrite custom circuits

The Core Tradeoff

Compact trades:

What you give upWhat you get
Turing-completenessAutomatic ZK circuit compilation
Dynamic typingStrong type safety enforced at compile time
Implicit privacyPrivacy model that works at the language level

This tradeoff is explicit and intentional. If you need full Turing-completeness, you don’t need Compact. But if you need privacy-preserving smart contracts and don’t want to write circuits by hand, Compact is purpose-built for exactly this.


Comparison Layer

FeatureSolidityRaw ZK (Circom)Compact
LanguageSolidityCircom/DSLTypeScript-like
Privacy modelNoneFullFull
Type safetyLooseManualEnforced
Learning curveLowVery highMedium
CompilationEVM bytecodeCircuitZK circuits + TS
State modelOn-chain onlyCustomPublic + private

Quick Recap

  • Compact bridges the gap between inaccessible raw ZK and privacy-free traditional contracts.
  • Midnight has two worlds: public (on-chain) and private (local). Only the proof goes on-chain.
  • Selective disclosure lets users reveal exactly what they choose, to whom they choose.
  • Compact trades Turing-completeness for automatic ZK circuit generation and strong type safety.
  • If you don’t need privacy, traditional contracts are simpler. If you need full control, raw circuits exist.
  • The type system is strict by design, it tracks data flow for privacy enforcement.