Build Tasks

Build targets, options, the build cache and build state.

elide build derives tasks from the manifest’s source sets and artifacts and runs them in dependency order. Tasks with unchanged inputs are skipped or restored from the cache.

Running the build

elide build                   # run the default task group
elide build compile-java-main # run one task by name
elide build compile           # run a whole task group
elide build clean             # the special clean target
elide build --inspect         # print the task graph and its options without running it
elide build --no-cache        # ignore cached results and build state; rebuild everything
elide build --offline         # no network: no dependency fetches, no shared cache
elide build --workers=4       # run at most four tasks at once

Targets

A bare argument names a task or group; a leading colon (:compile-java-main) is optional. No target runs default. A target that matches nothing fails the build.

GroupAliasTasks
default—What a plain elide build runs.
dependenciesdepsDependency resolution and install.
compilationcompileSource compilation.
testingtestTests; also run by elide test.

Some targets take options, listed by --inspect:

elide build test --select=class:com.example.SomeTest
elide build run --args="a b c"

In a workspace, prefix the project: core:compile-kotlin-main, core:compile, or core for its default tasks. Unqualified targets resolve in the current project, then the root. --inspect groups tasks by project, and progress rows show it ([core] Compiling Kotlin sources).

Options

Options are --name or --name=value, anywhere among the targets. Arguments after -- go to the process a task launches.

OptionEffect
--inspect, -iList tasks and their options without running.
--no-cacheDisable the cache and local build state; every task runs.
--offlineNo dependency downloads and no shared cache.
--workers=NAt most N concurrent tasks (default: processor count). = is required.
--insights=FILERun an insight script in tasks that run guest code; repeatable.
-f NAME[=VALUE]Build flag, read as build.flags; see Build Flags.

Options are checked against what the tasks declare before anything runs:

Unknown option '--worker', did you mean '--workers'?
Option '--workers' requires a value, as '--workers=<value>'

A value on a bare flag, or a repeated non-repeatable option, fails the same way. Global flags (-p, -v, --debug and the rest) are exempt. Task options: Dependencies, Testing.

Build cache

The local tier is always on: ~/.elide/cache/entries-v2, one directory per key with a record and a tar of the outputs. Restores are verified against the recorded fingerprint. Entries in an older format miss.

The shared tier is an HTTP cache, enabled only by environment variables:

VariableMeaning
ELIDE_REMOTE_CACHEEndpoint URL. Unset: no shared tier.
ELIDE_REMOTE_CACHE_TOKENBearer token; takes precedence over basic auth.
ELIDE_REMOTE_CACHE_USERNAME, ELIDE_REMOTE_CACHE_PASSWORDBasic auth; user info in the URL also works.
ELIDE_REMOTE_CACHE_PUSHUpload this build’s outputs (default true).
ELIDE_REMOTE_CACHE_PULLDownload misses (default true).
ELIDE_REMOTE_CACHE_POLICYeager (default) transfers every entry; smart transfers only when it saves time.
  • Local is checked first; remote hits are stored locally.
  • Typical setup: CI pushes; developers set ELIDE_REMOTE_CACHE_PUSH=false.
  • Unreachable, slow or unreadable remote entries are misses. After three consecutive transport failures the tier is off for the rest of the build. HTTP errors such as 404 are not transport failures; a rejected credential warns once.
  • The build fails on misconfiguration: a non-http/https URL, a password without a username, a non-boolean PUSH/PULL, or credentials sent over plain http to a non-loopback host.
  • The cache serves executable outputs: use https, require authentication for writes, and limit who can write.
  • --offline disables the shared tier for one run; --no-cache disables caching.

.eliderc and the smart policy

Under smart, an entry is downloaded only when that is cheaper than rebuilding, and uploaded only when the upload costs less than the work it saves. Costs come from .eliderc (java.util.Properties syntax): ~/.eliderc, then <project>/.eliderc over it. Do not commit it; it describes the machine.

# ~/.eliderc
network.downlink = 200mbps
network.uplink = 20mbps
network.latency = 250ms
network.stability = good        # good | fair | poor
machine.compute = fast          # slow | normal | fast, or a multiplier such as 1.5

cache.remote.policy = smart     # smart | eager (default)
cache.remote.upload-budget = 2.0
cache.remote.min-build = 500ms  # work cheaper than this is never published

Mb/s and mbps are megabits; MB/s is megabytes. Unreadable values warn and use the default. ELIDE_REMOTE_CACHE_POLICY overrides cache.remote.policy. Under eager, the file has no effect.

Build state

FileRole
.dev/elide.lock.v2.binPortable per-task fingerprints, shareable across machines. Not a dependency lockfile.
.dev/elide.build.binMachine-local per-task fingerprints.
.dev/elide.filehash.binFile digests keyed on size, times, inode and mode, so unchanged files are not re-read.
  • Binary files; do not edit.
  • There is no unified dependency lockfile; npm writes aube-lock.yaml.
  • In a workspace, state is stored in the root’s .dev/ for every member; outputs stay in each project’s .dev/.
  • --no-cache ignores the local state file but still reads the shared one.
  • elide install reuses resolution when the dependency list is unchanged; --fresh re-resolves.
  • Each compiler’s arguments are written beside its output as <tool>.args, one per line.

Timing a build

Each task prints its duration. For more:

elide build -v                                                # everything, at debug
ELIDE_LOG=dev.elide.tooling.build.telemetry=debug elide build # only the timings
[debug] dev.elide.tooling.build.telemetry stage graph took 590us
[debug] dev.elide.tooling.build.telemetry op compile-kotlin-main · up-to-date (up-to-date) took 420us
[debug] dev.elide.tooling.build.telemetry task compile-kotlin-main (skipped: up-to-date) took 12.6ms

Regions are a stage (configuration, graph, execution, state save), a task, or an operation on a task (prepare, fingerprint, up-to-date, execute, cache lookups and stores). Work inside execute is not split out.

ELIDE_BUILD_TELEMETRY writes a local Chrome trace when the build ends; nothing is uploaded:

ELIDE_BUILD_TELEMETRY=1 elide build             # .dev/telemetry/build-<stamp>.trace.json
ELIDE_BUILD_TELEMETRY=profile.json elide build  # a file you name
ELIDE_BUILD_TELEMETRY=/tmp/traces elide build   # a directory you name

Open it in Perfetto, chrome://tracing or speedscope, or:

jq -r '.traceEvents[] | select(.ph=="X") | "\(.dur/1000 | floor)ms \(.cat) \(.name)"' \
  .dev/telemetry/build-*.trace.json | sort -rn | head