Zinc is sbt’s incremental compiler for Scala, hosted in a separate repository at sbt/zinc. It’s the engine that enables sbt to recompile only the files that need recompilation, making builds dramatically faster.Documentation Index
Fetch the complete documentation index at: https://mintlify.com/sbt/sbt/llms.txt
Use this file to discover all available pages before exploring further.
What is Zinc?
Zinc wraps the Scala compiler and tracks dependencies between source files, classes, and external libraries. By analyzing what changed, Zinc can determine the minimal set of files that need recompilation.Key Innovation: Zinc doesn’t just track file modification times—it performs deep dependency analysis at the API level. A change to a method’s implementation won’t trigger recompilation of callers if the method’s signature didn’t change.
How Incremental Compilation Works
Initial Compilation
On the first compile, Zinc:
- Compiles all source files
- Records dependencies between sources and class files
- Extracts API signatures from compiled classes
- Stores this information in an Analysis file
Change Detection
On subsequent compiles, Zinc:
- Detects which source files changed (by hash, not timestamp)
- Identifies which APIs were modified
- Determines which files depend on the modified APIs
Minimal Recompilation
Zinc recompiles:
- Files that changed
- Files that depend on modified APIs
- Transitively affected files (if needed)
The Analysis File
The Analysis file (typically stored intarget/streams/*/compile/_global/streams/inc_compile_*.zip) contains:
- Source dependencies - Which sources depend on which sources
- Binary dependencies - Which sources depend on which class files
- External dependencies - Which sources depend on which library classes
- API signatures - Extracted API information for dependency tracking
- Compilation products - Mapping of sources to generated class files
Zinc Integration in sbt
ZincComponentCompiler
Thezinc-lm-integration module bridges Zinc with sbt’s library management system.
Key file: zinc-lm-integration/src/main/scala/sbt/internal/inc/ZincComponentCompiler.scala:1
- Compiles compiler bridges for each Scala version
- Manages component caching to avoid recompilation
- Resolves Scala compiler artifacts through library management
ZincComponentManager
Manages the lifecycle of Zinc components: Key file:zinc-lm-integration/src/main/scala/sbt/internal/inc/ZincComponentManager.scala:1
- Handles component locking for concurrent builds
- Provides component storage and retrieval
- Manages component versioning
Compiler Bridge
Zinc uses a compiler bridge to communicate with different Scala compiler versions:- Each Scala version requires its own bridge
- Bridges are compiled on-demand and cached
- The bridge implements the
xsbti.compileinterface
Name Hashing
Zinc uses a technique called name hashing to improve incremental compilation:- Tracks dependencies at the member level (methods, fields, types)
- Changes to private implementation don’t trigger recompilation of clients
- Only API changes propagate to dependent files
Compilation Phases
1. Analysis Phase
2. Compilation Phase
3. Persistence Phase
Key Concepts
API Extraction
API Extraction
Zinc extracts API information from compiled classes:
- Public method signatures
- Class hierarchies
- Type definitions
- Macro definitions
Invalidation
Invalidation
Zinc invalidates sources in several scenarios:
- Direct invalidation: Source file was modified
- API invalidation: A dependency’s API changed
- Transitive invalidation: Propagated from invalidated dependencies
External Dependencies
External Dependencies
Zinc tracks dependencies on external libraries:
- Records which sources use which library classes
- Triggers recompilation when library versions change
- Handles binary compatibility concerns
Macro Dependencies
Macro Dependencies
Scala macros require special handling:
- Macro implementations must be compiled before macro use sites
- Macro changes often require full recompilation of dependents
- Zinc tracks macro expansion dependencies
Configuration Options
Zinc behavior can be configured through sbt settings:incOptions- Fine-tune incremental compilation behaviorcompileOrder- Control Java/Scala compilation orderclassLoaderLayeringStrategy- Manage classloader isolation
Performance Characteristics
First Compilation
Slower than regular scalac due to analysis overheadCost: +10-20% compilation time
Incremental Builds
Dramatically faster for small changesSpeedup: 10-100x depending on change size
Full Rebuild
Similar to initial compilationUse: After
clean or analysis corruptionWarm Compiler
Resident compiler reduces JVM warmupSpeedup: 2-5x for repeated compilations
Troubleshooting
Compilation Inconsistencies
If you see unexpected compilation errors or missing dependencies:Check for corrupted analysis
Look for error messages mentioning “analysis” or “incremental compilation.”
Over-compilation
If Zinc is recompiling more than expected:-
Enable debug logging:
- Check for macro definitions: Macros often trigger broader recompilation
- Review API stability: Frequent API changes propagate to dependents
Under-compilation
If changes aren’t being picked up:- Verify source files are in the correct directory
- Check that timestamps are updating (some editors don’t)
- Run
cleanto reset compilation state
Tip: Use
sbt ~compile for continuous compilation during development. The ~ prefix watches for file changes and automatically recompiles.Zinc Architecture
Zinc is separate from sbt and can be used standalone:- xsbti - Binary interface between Zinc and compilers
- zinc-core - Core incremental compilation logic
- zinc-persist - Analysis serialization
- zinc-compile - High-level compilation APIs
- zinc-scripted - Testing framework for Zinc
Advanced Topics
Custom Compiler Plugins
Zinc supports compiler plugins but requires special consideration:- Plugins that modify APIs may affect incremental compilation
- Some plugins require full recompilation
- Configure with
scalacOptions
Zinc Server
sbt 2.x can run Zinc as a server for build tool integration:- Shared compilation across multiple clients
- Supports Build Server Protocol (BSP)
- See Build Server Protocol
Further Reading
Zinc Repository
Source code and detailed documentation
Architecture
How Zinc fits into sbt’s architecture
Compilation
User guide for compilation in sbt
Performance
Profiling and optimizing builds