Until today, a Mica compilation was described in exactly one place: the command line that invoked it. That was fine for the build — a Makefile remembers flags — but it left the editor guessing. The language server analyzed every file standalone, so a program importing a library it consumes through an emitted contract showed namespace not found on lines that built perfectly, and a utf-8 source was checked under utf-32 rules. The build knew the truth; the editor could not.

The fix that ships with 6.12.5 is deliberately small: a project file.

Three lines beside your sources

{
    "sources": ["Consumer.mica"],
    "encoding": "utf-8",
    "contracts": ["../build/Utilities", "../build/LibB"]
}

mica.project states the facts of a compilation — the things that belong to the source tree itself. Which files form the program. Which string encoding they are written against. Which libraries they consume, each named by the contract the compiler emitted when that library was built.

What it deliberately does not state are the choices of an invocation: the target architecture, the optimization tier, the build directory. Those stay on the command line, where they belong — the same tree builds for arm64 at O2 today and amd64 at debug tomorrow without the project file changing.

mica --compile --link --project . --build build --platform linux,arm64

Every explicit flag overrides its project entry, one fact at a time. A --platform that names no encoding is completed from the file.

The editor reads the same file

The language server discovers mica.project on its own, walking up from whatever file you have open — the way go.mod or compile_commands.json work. No settings, no configuration: open a source file, and the editor analyzes it under the same sources, the same encoding, and the same contracts the build uses.

In the tutorial repository every example now carries its project file, and the difference is visible the moment you open the interop examples: where the editor previously showed over a hundred false diagnostics across the library-consuming examples, it now shows exactly what the build would say — nothing.

Several libraries, several contracts

The project file’s contracts array carries a second change. Until now a compilation could consume one external contract file. A program that wanted two separately built libraries had no road — their contracts had to be merged by hand into a single file.

Both roads are now plural. On the command line:

mica ... --external-contract path/to/Utilities,path/to/LibB

and in the project file, as above. Each library keeps its own namespace, its imports are checked against its own emitted contract, and colliding names across contracts are refused at compile time:

imp
    Fibonacci, Sigmoid : Utilities;
    Triple, Announce   : LibB;

This is the first brick of something larger. A dependency set described by a file that both the build and the editor read is what a package manager generates — and that is the direction the project model is built to grow in.

When

The project model shipped with 6.12.5. The tutorial repository’s project files were published ahead of it — inert for older compilers, active the moment the release reaches your machine.

The same release carries the project model’s first payoff beyond the editor: mica --run compiles and executes one source file like a script — and because the run mode discovers mica.project exactly the way the language server does, a script beside your project imports your libraries with no flags at all. One release, one story: Mica gets projects, and becomes a scripting language.