Skip to content

Rule catalogue

devrepro explain <rule-id> prints any one of these. devrepro rules --catalog lists them all.

Every finding carries a rule id. There are 174 documented ids.

Two shapes exist. Most are written out in full where they are emitted. Some are composed at runtime from a tool or ecosystem name: multiple-installations takes whichever tool was found twice, so it is valid for any tool name and the entries below are representative rather than exhaustive. devrepro explain resolves any prefix.

abi/

abi/glibc-below-common-wheel-tag

glibc is older than the wheels most projects publish

What it means. The installed glibc is below the floor required by the manylinux tag the ecosystem has largely moved to.

Why it matters. Wheels carrying that tag are skipped silently and pip builds from source, which is how pip install numpy turns into a fifteen-minute compile that fails on a missing header. The finding names the tags this machine can install, because that is the part you can act on.

How to fix it. Use a newer base image or distribution release. Pinning older releases of each package works and is a treadmill; the glibc floor only moves in one direction.

abi/glibc-ok

glibc accepts the wheels most projects publish

What it means. The installed glibc meets the floor for current manylinux tags.

Why it matters. Recorded as a PASS because the absence of a finding and a verified match are different states, and a report that only lists problems cannot tell you which of the two it means.

How to fix it. Nothing to do.

abi/interpreter-arch-mismatch

The interpreter and the machine disagree about the architecture

What it means. The process asking for packages reports one architecture while the host reports another.

Why it matters. Package managers choose prebuilt artefacts by the interpreter's architecture, not the machine's, so everything installed through this interpreter is built for the wrong one. Installation succeeds every time; the cost appears as slow builds and as extensions that will not load elsewhere.

How to fix it. Reinstall the runtime for this machine's architecture. A runtime carried across from an Intel Mac by a migration assistant is the usual cause, and it keeps working well enough to go unnoticed.

abi/musl-libc

This machine uses musl, so manylinux wheels will not load

What it means. The C library is musl rather than glibc -- Alpine, and images derived from it, are the common case.

Why it matters. A manylinux wheel is linked against glibc and cannot load here. pip does not report that: it skips the wheel and builds from source instead, which needs a compiler and development headers that a slim image deliberately does not carry. The error names a missing header file, and the actual cause -- the C library -- is never mentioned.

How to fix it. Install the musllinux wheel where the project publishes one. Where it does not, add the build toolchain deliberately rather than discovering the need part-way through an install.

abi/runtime-arch-mismatch

A runtime reports a different architecture from the machine

What it means. node, go or a similar runtime answers with an architecture the host does not share.

Why it matters. Prebuilt native addons are selected by the runtime's own architecture. A mismatch means every one of them is the emulated build, and any addon compiled here will not load in a native process -- which is how a node_modules directory becomes non-portable between two machines that look identical.

How to fix it. Reinstall the runtime for this architecture and rebuild its native dependencies. For node, that is npm rebuild after removing node_modules.

abi/translated-process

This process runs under Rosetta translation

What it means. The interpreter is an x86_64 build running on Apple silicon, with macOS translating every instruction.

Why it matters. Nothing fails, which is the problem. Every package installed from here is the x86_64 build -- wheels, native addons, compiled extensions -- and they stay x86_64 for anything that loads them later. Builds take roughly ten times as long, and an extension compiled here will not load in a colleague's native arm64 process. The machine reports itself as arm64 throughout.

How to fix it. Install an arm64 build of the runtime and re-create the virtualenv or node_modules from scratch. Reinstalling packages into the existing one keeps the x86_64 artefacts that are already there.

advisories/

advisories/coverage

What the advisory set covers, and when it was reviewed

What it means. Names the advisory data in use, the date it was last reviewed, and the tools it has any data for at all.

Why it matters. An offline advisory set that is silent about a tool has given no answer, and silence reads as a clean result. Reporting coverage explicitly is the only thing that keeps those two apart. The date matters for the same reason: an old bundle is not a clean machine.

How to fix it. Nothing to fix. To use a different or newer set, run devrepro advisories --db <bundle.json>; an external bundle needs a signature beside it and DEVREPRO_ADVISORY_KEY set.

bazel/

bazel/cache-credential-committed

A build-cache credential is in a committed configuration file

What it means. nx.json, turbo.json or .bazelrc sets a field that holds a remote-cache token or an Authorization header. The field's presence is reported; its value is never read.

Why it matters. A read-write cache credential is a supply-chain secret: whoever holds it can write cache entries that every developer and every CI run then treats as trusted build output, without any of them fetching the source it supposedly came from. These files get committed without a second thought because they read like configuration rather than like secrets -- .bazelrc especially, which looks like a flags file.

How to fix it. Move it to an environment variable, which all three tools read, and rotate it: it is in the git history whether or not you delete the line now.

better-sqlite3/

better-sqlite3/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

buildtools/

buildtools/detected

A monorepo orchestrator is in use

What it means. Nx, Turborepo, Bazel or a similar tool is configured in this repository, together with whether it uses a remote cache.

Why it matters. Reported so that a cache is visible rather than assumed. A team that believes it has a shared cache and does not is wrong about why CI is slow, and a remote cache that is configured but unreachable costs more than none -- every task pays a lookup, fails it, and runs anyway.

How to fix it. Nothing to fix. Read from configuration files only; no orchestrator is invoked, because nx show projects and bazel info both start a long-lived daemon.

caches/

caches/compiler-cache-effective

The compiler cache is earning its place

What it means. The reported hit rate is high enough that the cache is saving more work than it costs.

Why it matters. Recorded as a PASS because the absence of a finding and a verified measurement are different states, and a report that only lists problems cannot tell you which of the two it means.

How to fix it. Nothing to do.

caches/compiler-cache-full

The compiler cache is at its configured size limit

What it means. Reported size has reached the maximum the cache was given.

Why it matters. A cache at its ceiling evicts what it is about to need again, which is usually the cause of a low hit rate rather than a separate problem. It is reported alongside the rate because the rate is the symptom and this is the thing to change.

How to fix it. Raise max_size (ccache) or SCCACHE_CACHE_SIZE. Both default to values chosen when repositories were smaller.

caches/compiler-cache-ineffective

The compiler cache is costing more than it saves

What it means. ccache or sccache reports a hit rate low enough that the cache is adding work rather than removing it.

Why it matters. Every miss pays a lookup, a write and an eviction on top of the compile it did not avoid. The usual cause is a cache smaller than the working set, so it evicts what it is about to need again. The symptom people report is "builds got slower after we turned caching on", which nobody attributes to the cache, and the numbers that would explain it are published by the cache itself and read by nothing.

How to fix it. Raise the size limit -- ccache --max-size or SCCACHE_CACHE_SIZE. If the cache is not full, look for something that varies on every run: an absolute path, a timestamp or a build id in the compiler command line defeats caching entirely.

caches/disk-critical

Free disk space is nearly exhausted

What it means. So little space remains that ordinary operations will fail.

Why it matters. A container build, a dependency install or even a git checkout will stop partway through, and the error will name whichever step happened to be running rather than the disk.

How to fix it. Reclaim space before doing anything else. docker system df and the cache inventory in this report both name candidates; neither is pruned automatically, because which data is expendable is not something a diagnostic can know.

caches/disk-low

Free disk space is low

What it means. Less space remains than a cold dependency install or a container image pull typically needs.

Why it matters. Enough for now, and not for the next npm ci or docker pull. The failure arrives mid-build as "no space left on device", from a step that has nothing to do with the cause.

How to fix it. Build caches are usually the largest reclaimable thing on a developer machine. This scan lists the ones present rather than sizing them -- walking a Gradle cache costs more than the whole scan -- and each finding carries the command that measures it.

caches/relocated

A build cache has been moved by an environment variable

What it means. One or more caches are not in their default location, because a variable such as PIP_CACHE_DIR or GRADLE_USER_HOME points elsewhere.

Why it matters. Usually deliberate and reported for one reason: a cache redirected onto a network share, an external volume, or a directory a cleanup job empties overnight is a common cause of "builds are slow on this machine only", with nothing in the build output that would explain it.

How to fix it. Nothing, if the redirection was intended. If it was not, unset the variable; the default location is on the fastest disk the machine has, which is normally the point.

canvas/

canvas/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

containers/

containers/arch-emulated

The container engine is emulating another architecture

What it means. The daemon reports a different CPU architecture from the host, so every build and every container runs through qemu.

Why it matters. It works, which is why nobody notices. It is also roughly ten times slower, and the usual cause is a base image with no manifest for the host architecture -- so one line in a Dockerfile silently turns a one-minute build into a twenty-minute one.

How to fix it. Use a base image that publishes your architecture, or pass --platform explicitly so the emulation is a decision rather than a surprise. If the target really is the other architecture, nothing here is wrong.

containers/buildkit-unavailable

docker buildx is not available

What it means. The daemon answers, but the buildx plugin is absent, so builds fall back to the legacy builder.

Why it matters. Multi-platform builds, build secrets, cache mounts and --mount=type=cache all require BuildKit. A Dockerfile using any of them fails with a syntax error rather than a message about the builder, which sends people looking in the wrong file.

How to fix it. Install the buildx plugin from your package manager, or use a Docker distribution that bundles it. Nothing needs changing if no Dockerfile here uses BuildKit features.

containers/cgroup-v1

The container engine is using cgroup v1

What it means. Resource limits are enforced through the first-generation cgroup interface rather than the unified hierarchy.

Why it matters. Memory accounting differs between the two, so a container that is OOM-killed on a v2 CI runner can pass locally on v1 and the other way round. Swap accounting is often absent entirely under v1, which makes --memory mean something different from what the docs say.

How to fix it. Enable unified cgroups on the host, or switch it on in Docker Desktop's settings. On a distribution still defaulting to v1, systemd.unified_cgroup_hierarchy=1 on the kernel command line does it.

containers/devcontainer-required

Policy requires a devcontainer definition

What it means. The policy sets require_devcontainer, and no .devcontainer/devcontainer.json was found.

Why it matters. The team decided one-command reproducible environments are the standard here, and this repository does not meet it.

How to fix it. Run devrepro generate devcontainer for a reviewable draft, then adjust and commit it.

containers/disk-reclaimable

Container storage holds a large amount of reclaimable space

What it means. The daemon's own accounting says a substantial share of its images, volumes and build cache is unreferenced.

Why it matters. Running out of space mid-build produces one of the least informative errors in the ecosystem -- no space left on device, from a step that has nothing to do with the cause -- and it usually arrives with tens of gigabytes of dangling layers sitting behind it. Reporting it before it becomes that error is the only useful moment.

How to fix it. docker system prune -a --volumes reclaims it. This tool does not run it and will not offer to: pruning deletes data, and which data is expendable is not something a diagnostic can know.

containers/docker-daemon-error

Docker daemon returned an error this project does not classify

What it means. docker info failed with a message that matched none of the known patterns.

Why it matters. Reported verbatim rather than guessed at. A specific wrong diagnosis would send you further from the cause than an honest unknown.

How to fix it. Read the evidence excerpt in the finding; it carries the daemon's own message. If the shape is common, it is worth a classifier branch.

containers/docker-daemon-permission

Docker daemon refused this user

What it means. The daemon is running, but this user is not permitted to talk to its socket.

Why it matters. Every container command fails with a permission error that looks like the daemon is down. It is not: the daemon is fine and the user is not in the right group.

How to fix it. On Linux, add your user to the docker group and start a new login session. Prefer that to running the CLI with sudo, which leaves root-owned files in your build outputs.

containers/docker-daemon-pipe-missing

Docker Desktop's named pipe is absent

What it means. The CLI tried to reach the daemon over its Windows named pipe and the pipe does not exist.

Why it matters. This is what a stopped Docker Desktop looks like from the CLI's side. The message names the pipe rather than the application, so it reads like a configuration fault when it is simply not running.

How to fix it. Start Docker Desktop and wait for it to report running, then re-run devrepro doctor.

containers/docker-daemon-unreachable

Docker CLI present, daemon not answering

What it means. The docker command exists, but docker info cannot reach a daemon.

Why it matters. Every container-based build, test and devcontainer fails until the daemon is running. The CLI being installed makes this look like a working setup when it is not.

How to fix it. Start Docker Desktop, or systemctl start docker on Linux. On Windows check that the WSL backend is healthy.

containers/docker-docker-wsl-backend-error

Docker's WSL backend is unhealthy

What it means. The daemon could not be reached and the error names WSL.

Why it matters. Docker Desktop on Windows runs its engine inside WSL2. When that distribution is stopped, corrupt, or was updated underneath Docker, the CLI reports a connection failure that is really a WSL failure.

How to fix it. Check wsl --list --verbose and wsl --status. Restarting WSL (wsl --shutdown, then start Docker Desktop) resolves most of these.

containers/docker-missing

Docker CLI not installed

What it means. No docker executable resolves on PATH.

Why it matters. Reported as INFO, not an error: plenty of projects never need it. It matters only when the project declares a container requirement.

How to fix it. Install Docker only if this project needs it. devrepro project shows what is actually declared.

containers/healthy

Container tooling is healthy

What it means. The container runtime responded normally.

Why it matters. Reported so a working container stack is visible in the report rather than inferred from the absence of an error.

How to fix it. No action needed.

containers/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

containers/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

containers/multiple-runtimes

More than one container engine is installed

What it means. Two or more of Docker Desktop, Colima, Rancher Desktop, OrbStack, Podman, Lima and minikube resolve on PATH.

Why it matters. This is not a fault -- plenty of people keep Colima beside Docker Desktop deliberately. It is worth knowing because it makes docker context load-bearing: a context pointing at a stopped VM produces exactly the error you would get with no daemon at all, and the obvious fix (start Docker Desktop) then changes nothing.

How to fix it. docker context ls shows which engine docker currently talks to, and docker context use <name> switches it.

containers/state-unknown

Container state could not be determined

What it means. The probe could not establish whether container tooling works.

Why it matters. Reported as unknown rather than healthy. A diagnostic that guesses is worse than one that admits the gap.

How to fix it. Run docker info by hand to see what it says.

containers/storage-driver-legacy

The storage driver is deprecated, removed, or has no copy-on-write

What it means. The daemon is using a storage driver that current engines no longer recommend or no longer ship.

Why it matters. aufs and devicemapper are removed in recent Docker releases, so an upgrade will stop the daemon starting. vfs is the one that surprises people: it is correct, it is what you get when nothing else is available, and it copies the entire filesystem for every layer.

How to fix it. Move to overlay2. Changing the storage driver discards existing images and containers, so do it when you can afford to rebuild rather than in the middle of something.

containers/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

containers/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

containers/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

cpp/

cpp/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

cpp/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

cpp/no-compiler

No C/C++ compiler found

What it means. No MSVC, gcc or clang resolves on PATH.

Why it matters. Native extensions cannot build. This surfaces late and confusingly: pip install or npm install fails deep inside a build log rather than saying a compiler is missing.

How to fix it. Install build tools for your platform -- Visual Studio Build Tools, Xcode Command Line Tools, or your distribution's build-essential.

cpp/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

cpp/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

cpp/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

django/

django/runtime-missing

A framework needs a runtime that does not resolve here

What it means. The project depends on a framework requiring a runtime, and that runtime is not on PATH at all.

Why it matters. Nothing about this project will build. Reported separately from a version mismatch because the fix is different: one is an upgrade, the other is an install -- or a PATH problem, which devrepro which answers.

How to fix it. Install the runtime, then check devrepro which <tool>: it is often installed and shadowed, which looks identical from here.

django/runtime-ok

The framework's runtime floor is met

What it means. The installed runtime satisfies the floor this project's framework requires.

Why it matters. Nothing to do. Reported so a satisfied requirement is visible rather than inferred from the absence of a complaint.

How to fix it. No action needed.

django/runtime-too-old

A framework needs a newer runtime than this machine has

What it means. The framework this project depends on requires a runtime floor its own manifest does not state -- Next.js pins a Node version per major, Django pins a Python version, Spring Boot pins a JDK.

Why it matters. This is the case where every declared range is satisfied and the build still fails, because the requirement is one layer below the manifest. It also fails with a message that names something other than the cause: a syntax error rather than a Node version, a bytecode class-version number rather than a JDK.

How to fix it. Install a runtime at or above the floor named in the finding, and consider stating it in the project's own manifest -- engines in package.json, requires-python in pyproject.toml -- so the next person learns it from the file rather than from a build failure.

docker/

docker/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

dotnet/

dotnet/global-json-satisfied

An installed .NET SDK satisfies global.json

What it means. One of the SDKs on this machine matches the pin under its rollForward policy.

Why it matters. Recorded as a PASS because the absence of a finding and a verified match are different states, and a report that only lists problems cannot tell you which of the two it means.

How to fix it. Nothing to do.

dotnet/global-json-sdk-missing

global.json pins a .NET SDK that is not installed

What it means. The repository's global.json requests an SDK version, and no installed SDK satisfies it under the file's rollForward policy.

Why it matters. dotnet build fails with "A compatible .NET SDK was not found", while dotnet --version prints one of the SDKs that is installed and every other check passes -- which is why this reads as a working installation right up until the build. With rollForward unset the pin is exact to the feature band, so 8.0.100 and 8.0.404 are not interchangeable.

How to fix it. Install the pinned SDK, or set rollForward in global.json if a newer one is genuinely acceptable. Deleting the pin works and gives up the reason it was added.

dotnet/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

dotnet/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

dotnet/sdk-list-unavailable

The installed .NET SDKs could not be listed

What it means. global.json pins an SDK, but dotnet --list-sdks did not answer.

Why it matters. Whether the pin is satisfiable here is genuinely unknown, and reporting it as a blocker would be a guess. This is UNKNOWN rather than BLOCKED for that reason.

How to fix it. Install the .NET SDK if this project is built on this machine. If it is not, nothing here needs changing.

dotnet/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

dotnet/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

dotnet/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

editor/

editor/style-conflict

The editor and the formatter have been told different things

What it means. .editorconfig declares an indent style, width or line length that a configured formatter (prettier, ruff) contradicts.

Why it matters. The editor formats one way as you type and the formatter rewrites it the other way on save or in a hook. The result is a whitespace diff nobody can attribute, on a two-line change, and the reviewer blames the author. Both tools are behaving exactly as configured, which is why nobody finds the cause.

How to fix it. Pick one and make the other match. Whichever tool runs in CI is the one that decides, so .editorconfig should usually change to match the formatter rather than the reverse. Settings neither side has configured are not compared: a default is not a disagreement.

env/

env/credential-names-present

Credential-shaped variable names in this session

What it means. Variables whose NAMES look like credentials exist in the environment. Their values are never read.

Why it matters. Informational, and deliberately name-only: it tells you secrets are present in this shell without ever handling them.

How to fix it. No action needed. It is context for anyone reading the report.

env/required-names-present

Required environment variable names

What it means. Whether the variable NAMES the policy requires are set. Values are never read, printed or stored.

Why it matters. Missing configuration surfaces as a runtime failure far from the cause. Checking names catches it before the process starts.

How to fix it. Set the missing variables in your shell profile or .env loader.

git/

git/credential-helper-missing

A credential helper is configured but not installed

What it means. credential.helper names a helper that resolves to no program in git's exec directory or on PATH.

Why it matters. Every authenticated fetch, clone and push falls back to prompting. Interactively that is a confusing password request for a repository you thought was public; in CI it is a hang followed by a timeout, and nothing in the output names the helper. The setting usually survives a machine migration or an OS change that the helper did not.

How to fix it. Install the helper, or clear the setting with git config --global --unset credential.helper. devrepro reads the helper's name and never runs it -- several of them block on stdin.

git/credential-store-plaintext

The store credential helper keeps tokens in plain text

What it means. credential.helper=store writes credentials to ~/.git-credentials unencrypted.

Why it matters. Reported as information rather than a problem: on a single-user machine it is a considered choice, and it is the only helper that works everywhere. It is worth knowing because the file is readable by anything running as you -- including any package postinstall script -- and because backups and sync tools copy it without asking.

How to fix it. An OS keychain helper (osxkeychain, wincred, libsecret) or Git Credential Manager stores the same tokens encrypted. devrepro reports the setting and never reads the file.

git/known-advisory

The installed tool version is covered by a published advisory

What it means. The version of this build tool matches an entry in the offline advisory set that ships with devrepro, or in the bundle you supplied with --db.

Why it matters. Dependency scanners never look at the compiler, the interpreter or git, because none of them appear in a lockfile. A toolchain can therefore sit years out of date behind a perfectly clean audit.

How to fix it. Upgrade the tool to the fix on its own release branch -- backported fixes mean the highest version number is not always the answer. This comparison is offline and does not know whether your distribution backported the fix into the version string you have, which many do; check your distribution's changelog before treating it as urgent.

git/lfs-not-initialised

Git LFS is installed but its filters are not configured

What it means. git lfs exists, but filter.lfs.smudge is unset for this user and repository, so the clean/smudge filters never run.

Why it matters. Same symptom as not having LFS at all -- pointer files in the working tree, a clean git status -- and a different fix, which is why the two are separate findings rather than one. Being told to install something already installed is how a person concludes the tool is wrong and stops reading it.

How to fix it. git lfs install configures the filters; git lfs pull fetches what the current checkout missed.

git/lfs-ready

Git LFS is installed and configured for this checkout

What it means. The repository declares LFS-tracked paths and the filters are in place.

Why it matters. Recorded as a PASS because the absence of a finding and a verified match are different states, and a report that only lists problems cannot tell you which of the two it means.

How to fix it. Nothing to do.

git/lfs-required-not-installed

This repository needs Git LFS and it is not installed

What it means. A .gitattributes here routes files through filter=lfs, and git lfs does not resolve on this machine.

Why it matters. Git does not fail. It writes the pointer files -- a few lines of text where a binary should be -- reports the working tree as clean, and leaves the failure for whatever opens those files later. The error you get says the image is corrupt or the archive ended unexpectedly, and names a file rather than a missing tool.

How to fix it. Install git-lfs, run git lfs install, then git lfs pull to replace the pointers already in your working tree. Cloning again without installing LFS first produces the same pointers.

git/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

git/partial-clone

This is a partial clone; some objects are fetched on demand

What it means. A filter such as blob:none or tree:0 is configured on the remote, so objects arrive lazily rather than at clone time.

Why it matters. It is a deliberate and usually good trade. It matters here because an operation needing a missing blob reaches the network, and on an air-gapped or simply offline machine that failure reads as repository corruption rather than as a fetch that could not happen.

How to fix it. Nothing, unless you work offline: git fetch --refetch with no filter materialises what is missing.

git/shallow-clone

This is a shallow clone

What it means. History before the graft point is absent, usually from a --depth clone or a CI checkout that defaults to depth 1.

Why it matters. git describe produces the wrong version or fails, git blame stops at the graft, and any diff against a base ref -- including the one devrepro guard --scope changed uses -- cannot resolve the base. None of those errors mention shallowness.

How to fix it. git fetch --unshallow. In GitHub Actions, fetch-depth: 0 on the checkout step; most CI systems have an equivalent.

git/sparse-checkout-active

Sparse checkout is on, so parts of the tree are deliberately absent

What it means. core.sparseCheckout is enabled and a pattern list decides which paths are materialised.

Why it matters. This is normally deliberate and is reported rather than warned about. It earns a place because a build failing on a path that exists in the repository and not on disk has no other visible explanation -- git status is clean either way, and the file is present in every listing on the web.

How to fix it. git sparse-checkout list shows what is included and git sparse-checkout disable restores the full tree. Nothing here needs changing if the narrowing was intended.

git/submodules-uninitialised

Declared submodules have not been checked out

What it means. .gitmodules names submodules whose directories are empty.

Why it matters. An uninitialised submodule is an empty directory, not an error, so a build fails on a missing header or a missing module rather than on a missing submodule. git status says nothing, because as far as the outer repository is concerned nothing has changed.

How to fix it. git submodule update --init --recursive. Adding --recurse-submodules to your clone avoids the state entirely.

go/

go/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

go/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

go/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

go/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

go/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

go/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

gpu/

gpu/cuda-compatible

The CUDA toolkit and the driver agree

What it means. The installed toolkit falls inside the major version the driver supports.

Why it matters. Nothing to do. Reported so that a working CUDA setup is visible rather than inferred from the absence of a complaint.

How to fix it. No action needed.

gpu/cuda-driver-old

Driver too old for the installed CUDA toolkit

What it means. The NVIDIA driver version does not support the CUDA toolkit present.

Why it matters. This is the specific incompatible pair, rather than the 'CUDA not found' that frameworks usually report. Training and inference either fail at load or silently fall back to CPU.

How to fix it. Update the driver to one that supports the toolkit, or install a toolkit matching the driver.

gpu/cuda-driver-too-old

The installed CUDA toolkit needs a newer driver than this one

What it means. The CUDA toolkit's major version is ahead of the highest CUDA runtime the installed NVIDIA driver can run, as the driver itself reports it.

Why it matters. Anything built with nvcc fails at launch with 'CUDA driver version is insufficient for CUDA runtime version', which names neither version. People reinstall the toolkit, or the driver, more or less at random.

How to fix it. Update the NVIDIA driver, or install a toolkit inside the major version the driver supports. Note that CUDA 11+ guarantees minor-version compatibility, so 12.4 on a driver reporting 12.2 is fine and is not what this reports. To see what a framework build expects: python -c "import torch; print(torch.version.cuda)".

gpu/cuda-toolkit-absent

A driver is present and nvcc is not

What it means. nvidia-smi answered but no CUDA toolkit is on PATH, so the compiler half of the stack is unknown.

Why it matters. Reported as information, not as a fault. A framework wheel ships its own CUDA runtime and never calls nvcc; the toolkit matters only if you compile CUDA code yourself.

How to fix it. Install the CUDA toolkit only if you build CUDA sources. Otherwise nothing is missing.

gpu/cuda-toolkit-missing

NVIDIA GPU present, CUDA toolkit absent

What it means. A driver was detected but no CUDA toolkit was found.

Why it matters. Frameworks fall back to CPU, usually without saying so clearly. The symptom is a job that runs but takes a hundred times longer.

How to fix it. Install a CUDA toolkit compatible with the driver, or use a framework build that bundles its own runtime.

gpu/mixed-architectures

The GPUs in this machine have different compute capabilities

What it means. Two or more devices report different sm_XX architectures.

Why it matters. A build targeting one architecture produces kernels the other card cannot execute, and the failure -- 'no kernel image is available for execution on the device' -- names neither the device nor the architecture. It also arrives at runtime, on whichever device the scheduler happened to pick, so it looks intermittent.

How to fix it. Build for every architecture present (TORCH_CUDA_ARCH_LIST or CMAKE_CUDA_ARCHITECTURES covering them all), or pin the job to one device with CUDA_VISIBLE_DEVICES.

gpu/no-accelerator

No GPU accelerator detected

What it means. No NVIDIA, ROCm, oneAPI, Metal or DirectML stack was found.

Why it matters. Informational. It matters only if the project expects acceleration.

How to fix it. No action needed on a CPU-only machine.

gpu/stack-detected

GPU/AI stack detected

What it means. An accelerator stack was found and its versions recorded.

Why it matters. Recorded so a snapshot diff can show when the stack changes -- one of the most common causes of a model that trains on one machine only.

How to fix it. No action needed.

gpu/state-unknown

GPU state could not be determined

What it means. The probe could not establish what accelerator stack is present.

Why it matters. Reported as unknown rather than absent.

How to fix it. Run nvidia-smi or the equivalent for your vendor by hand.

host/

host/antivirus-not-defender

Defender's real-time protection is off, so its exclusions mean nothing

What it means. Defender answered and reported real-time protection disabled. On a machine that is not unprotected this usually means another antivirus product registered itself and Defender stood down.

Why it matters. That other product's exclusion list is not visible from here, so this check cannot speak for whatever is actually scanning your build directories -- and scanning is a common cause of a Windows build being several times slower than the same build elsewhere.

How to fix it. Nothing to fix here. If Windows builds are slow, check your antivirus product's own exclusion list for the project's dependency and output directories.

host/antivirus-scans-build-dirs

Real-time scanning inspects this project's build directories

What it means. Windows Defender's real-time protection is on and its exclusion list does not cover the dependency and output directories this project actually has.

Why it matters. Every file a build opens is scanned synchronously, on files written seconds earlier by a tool the machine already trusts. This is routinely the largest single factor in a Windows build taking several times longer than the same build elsewhere, and it is invisible: nothing fails and nothing logs.

How to fix it. Excluding them is a trade, not a fix: it is a genuine reduction in protection on a tree whose install scripts execute code you did not write. Whether it is worth it depends on the machine and on your organisation's rules. DevRepro changes nothing -- the finding carries the exact command if you decide it is.

host/antivirus-unknown

Defender's configuration could not be read from this shell

What it means. Get-MpComputerStatus or Get-MpPreference did not answer. This is almost always a permissions result rather than an absent Defender.

Why it matters. Reported rather than assumed, because from a non-elevated shell 'could not read the exclusions' and 'there are no exclusions' look identical and lead to opposite conclusions.

How to fix it. Run devrepro doctor from an elevated shell to see which build directories real-time scanning inspects.

host/clock-unsynchronised

Nothing is correcting this machine's clock

What it means. No time-synchronisation service is running, or the configured source is the machine's own hardware clock -- which is synchronising with itself and correcting nothing.

Why it matters. The clock has not drifted yet; it will. When it does, the first symptom is usually a TLS error blaming a certificate that is fine ('not yet valid', 'expired'), and somebody spends an afternoon on the certificate. It also breaks Kerberos outright and makes build tools rebuild -- or refuse to rebuild -- for reasons no log explains. This is the cause; clock skew is the symptom, detected separately and later.

How to fix it. Windows: w32tm /config /syncfromflags:domhier /update on a domain machine, or point it at time.windows.com and start the Windows Time service. Linux: enable systemd-timesyncd or chrony.

host/slow-filesystem

The project is on a filesystem where every file operation is slow

What it means. The source tree sits on a WSL/Windows crossing, a network share or another mount where each file operation costs a millisecond instead of a microsecond.

Why it matters. A dependency install performs hundreds of thousands of file operations. Three orders of magnitude on each is the difference between twenty seconds and twenty minutes -- and nothing is failing, so no profiler anybody runs will point at it. It reads as a slow build tool, which is where people go looking.

How to fix it. Move the tree onto local storage. Inside WSL that means somewhere under ~, opened from the editor's WSL integration rather than through /mnt/c. On a network share, at minimum keep the dependency directory local -- most package managers accept a store or cache path outside the project.

hygiene/

hygiene/filesystem-case

Filesystem case sensitivity

What it means. Whether this filesystem distinguishes Config.py from config.py.

Why it matters. Linux is case-sensitive; Windows and macOS are not, by default. A repository authored on Linux that contains two files differing only in case loses one of them on checkout elsewhere, with no error at any point -- git reports success and the working tree is wrong.

How to fix it. Nothing to change about the filesystem. Avoid committing paths that differ only in case; git config core.ignorecase affects how git compares them but not what the filesystem stores.

hygiene/non-utf8-locale

Text encoding is not UTF-8

What it means. The preferred encoding a subprocess inherits is a legacy codepage rather than UTF-8.

Why it matters. Any tool that writes a non-ASCII character to this console can die with UnicodeEncodeError, and filenames with accents may not round-trip. This project hit exactly that: a single arrow in a remediation hint ended devrepro check on a cp1252 console.

How to fix it. Set PYTHONUTF8=1 for Python tools, or enable the OS-wide UTF-8 option (Windows: Region settings, 'Beta: Use Unicode UTF-8'). Note that the OS-wide switch affects every application, so it is worth changing deliberately rather than casually.

hygiene/reserved-filename

A path uses a name Windows reserves

What it means. The repository contains a path whose name is a DOS device name -- con, prn, aux, nul, com1-com9 or lpt1-lpt9 -- with or without an extension, so aux.js counts.

Why it matters. Windows cannot create the file at all. The clone fails with an error that names neither the file nor the reason, and the repository is simply unusable there.

How to fix it. Rename the path. This is reported on every platform on purpose: the person who can still fix it cheaply is the one about to commit it, not the one who cannot clone it.

This process cannot create symlinks

What it means. On Windows, symlink creation needs Developer Mode or SeCreateSymbolicLinkPrivilege, and neither is available here.

Why it matters. Git does not fail when it cannot create a symlink. It writes an ordinary file containing the link target instead, so the working tree differs from the commit while git status reports everything clean.

How to fix it. Enable Developer Mode in Windows Settings, or work inside WSL where symlinks behave normally.

java/

java/home-path-mismatch

JAVA_HOME and the java on PATH are different JDKs

What it means. The JDK that JAVA_HOME points at reports a different version from the java the shell resolves.

Why it matters. Maven and Gradle use JAVA_HOME; a shell script that calls java directly uses PATH. When they disagree, the build compiles against one JDK and runs on another, and the failure is an UnsupportedClassVersionError that names neither of them.

How to fix it. Point JAVA_HOME at the JDK you intend to use and put its bin first on PATH. A toolchain block in the build file overrides both, so check that too if one is declared.

java/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

java/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

java/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

java/multiple-jdks

Several JDKs are installed

What it means. More than one JDK was found in the usual installation directories.

Why it matters. Not a fault -- most Java developers need several. It is worth knowing because which one a build uses depends on JAVA_HOME, on PATH, and on whichever toolchain block the build file declares: three settings that are frequently out of step, and none of which announces itself.

How to fix it. Nothing, unless a build behaves unexpectedly. java -version and echo $JAVA_HOME together tell you which two of the three agree.

java/shim-bypassed

A version manager is installed but not being used

What it means. The manager's shim directory is on PATH, but another installation of this tool resolves before it.

Why it matters. The manager still reports the version it intends -- pyenv version says 3.12 -- while every command gets something else, because resolution is decided by PATH order and nothing else. Neither tool is wrong about what it was asked, so nothing reports a problem, and the project's pinned version is quietly not in effect.

How to fix it. Move the manager's shim directory earlier in PATH than the installation that currently wins. devrepro which <tool> lists every candidate in precedence order. Note that an IDE's integrated terminal often has a different PATH from a login shell, so check the one you actually build in.

java/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

java/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

java/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

kubectl/

kubectl/context-not-local

kubectl's current context may point at a production cluster

What it means. The current kubeconfig context is not one of the local clusters this machine runs, and its name contains a marker like prod or live.

Why it matters. The context is global to your user, persists across shells and reboots, and does not appear in a normal prompt. Every regretted kubectl delete was typed into a shell whose context the person believed was something else. This is blast radius, in the same sense agent-check uses the term.

How to fix it. Confirm with kubectl config current-context, and consider a prompt segment that shows it. Note this is a guess from the context name: reading the cluster to be certain would mean an authenticated request to a production cluster from a diagnostic command, which is not a trade this tool makes.

lockfiles/

lockfiles/format-supported

The installed manager can use this lockfile

What it means. The package manager on PATH is at or above the floor this lockfile format requires.

Why it matters. Recorded as a PASS because the absence of a finding and a verified match are different states, and a report that only lists problems cannot tell you which of the two it means.

How to fix it. Nothing to do.

lockfiles/format-unknown

The manager is installed but did not report a version

What it means. The package manager resolves on PATH, but asking it for its version produced nothing, so whether it can read the lockfile is unknown.

Why it matters. Reported as UNKNOWN rather than folded into 'not installed', because the two have different fixes and conflating them sends you looking for a missing program that is right there. A common cause on Windows is a wrapper script resolving ahead of the real executable.

How to fix it. Run the manager's --version by hand. If that works, the resolution order on PATH is the problem rather than the installation; devrepro path shows what resolves first.

lockfiles/manager-missing

A lockfile with no package manager to read it

What it means. The repository contains a lockfile for a package manager that does not resolve on PATH.

Why it matters. Nothing installs from it. This is a warning rather than a blocker because it is often correct: a project that moved from yarn to pnpm and left the old lockfile behind is untidy, not broken.

How to fix it. Install the manager if the lockfile is current, or delete the lockfile if the project has moved on. Leaving both a yarn.lock and a package-lock.json in one directory means two machines can resolve two different dependency trees from the same commit.

lockfiles/runtime-mismatch

The active runtime is outside the range this lockfile was solved for

What it means. The lockfile records the runtime range it resolved against -- requires-python, engines.node, RUBY VERSION -- and the runtime on PATH falls outside it.

Why it matters. A dependency graph is solved for a specific runtime range. Installing it on a runtime outside that range gives you packages whose own constraints were never checked against what you are running, and the failure appears at import or build time rather than at install time.

How to fix it. Switch to a runtime inside the recorded range for this project, or re-resolve the lockfile on the runtime you intend to use and commit the result. Do not install across the boundary and hope.

lockfiles/runtime-spec-unparseable

The lockfile pins a runtime range this tool cannot parse

What it means. The recorded range uses ecosystem shorthand -- npm's ^20, pip's ~=3.11 -- that this project's version comparison does not implement.

Why it matters. Reported rather than skipped so the gap is visible. A tool that silently ignores a constraint it cannot read is indistinguishable from one that checked and found no problem.

How to fix it. Check the range by hand against the runtime you are using. Comparator syntax (>=20, >=3.11,<3.13) is understood and can be used in .devrepro.toml if you want this enforced.

lockfiles/tool-too-old

The package manager is older than the lockfile format

What it means. This lockfile is written in a format version that the installed package manager predates.

Why it matters. The manager does not usually refuse. npm 6 handed a lockfileVersion: 3 file rewrites the entire tree in the old format, and cargo before 1.78 cannot read a version = 4 Cargo.lock at all. The first outcome is worse than the second: the install appears to succeed and the damage arrives as an unreviewable diff in someone else's pull request.

How to fix it. Upgrade the package manager to the version the format requires. Downgrading the lockfile instead means every other machine that already has the newer manager re-upgrades it, and the file thrashes.

lockfiles/unreadable

The lockfile could not be parsed

What it means. The file exists but is not valid JSON, TOML or the text format its name implies -- usually a merge conflict left in place, or a truncated write.

Why it matters. A lockfile that cannot be parsed cannot reproduce anything, and the error a package manager gives for one is rarely about the file.

How to fix it. Regenerate it with its package manager rather than hand-editing. If the cause was a merge conflict, resolve the manifest first and then re-lock; resolving conflict markers inside a lockfile by hand produces a file that parses and is still wrong.

mysqlclient/

mysqlclient/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

network/

network/ca-bundle-missing

A CA bundle variable points at a file that is not there

What it means. NODE_EXTRA_CA_CERTS, REQUESTS_CA_BUNDLE or a sibling names a path that does not exist.

Why it matters. The runtime falls back to its default trust store and the override does nothing, silently. Whoever set it believes the corporate CA is trusted, and it is not.

How to fix it. Correct the path, or unset the variable so the fallback is deliberate rather than accidental.

network/checks-skipped

Endpoint and TLS checks did not run, because they open connections

What it means. A scan reports proxy configuration -- read from environment variables, which needs no connection -- and stops there. Reachability and TLS checks require opening sockets to github.com, the npm registry and PyPI, and a scan does not do that unless asked.

Why it matters. Reported rather than left silent, because a scan that says nothing about network health reads as a scan that found network health fine. Until this was fixed, these checks ran on every scan: three third-party hosts, and any proxy in the path, learned that this machine had run this tool.

How to fix it. Run devrepro doctor --allow-network, or devrepro network --allow-network for the fuller DNS, TLS and registry diagnostics.

network/clock-skew

System clock is significantly wrong

What it means. The system clock differs from network time by more than the tolerated margin.

Why it matters. TLS certificate validation fails when the clock is far enough off, which breaks package installs, git over HTTPS and container pulls with errors that blame the certificate rather than the clock.

How to fix it. Enable automatic time synchronisation for your OS.

network/endpoint-unreachable

A development endpoint did not respond

What it means. One of the checked registries or hosts was unreachable, or its TLS chain did not validate.

Why it matters. Package installs will fail. Behind a corporate proxy this is usually TLS interception rather than an outage.

How to fix it. Check proxy settings and whether your organisation's CA is trusted by the language runtime you are using -- Node, Python, Go and Java each keep their own trust store.

network/endpoints-ok

Development endpoints reachable

What it means. The checked registries responded with a valid TLS chain.

Why it matters. Reported so a working network path is visible in the report.

How to fix it. No action needed.

network/registry-override

Packages come from somewhere other than the public registry

What it means. An .npmrc, pip.conf, .cargo/config.toml or similar points at a mirror or proxy.

Why it matters. Normal on its own -- mirrors exist for good reasons. It matters when one machine has the override and another does not: the same install command then fetches different bytes, the lockfile still matches, and nothing reports a difference. A user-scoped override is the harder case, because it is invisible to everyone else on the team.

How to fix it. Confirm the whole team shares the configuration, and prefer a project-scoped file over a user-scoped one so it is reviewable.

network/trust-store-partial

Some runtimes trust the corporate CA and others do not

What it means. A custom CA bundle is configured for at least one ecosystem and not for others.

Why it matters. Every runtime keeps its own trust store: Node reads NODE_EXTRA_CA_CERTS, Python REQUESTS_CA_BUNDLE, Go SSL_CERT_FILE, git GIT_SSL_CAINFO. Behind a TLS-intercepting proxy, configuring one means npm install works and pip install fails on the same machine, with an error that blames the certificate rather than the missing variable.

How to fix it. Set the corresponding variable for each ecosystem you use. There is no single setting that covers them all, which is the whole difficulty.

next/

next/runtime-missing

A framework needs a runtime that does not resolve here

What it means. The project depends on a framework requiring a runtime, and that runtime is not on PATH at all.

Why it matters. Nothing about this project will build. Reported separately from a version mismatch because the fix is different: one is an upgrade, the other is an install -- or a PATH problem, which devrepro which answers.

How to fix it. Install the runtime, then check devrepro which <tool>: it is often installed and shadowed, which looks identical from here.

next/runtime-ok

The framework's runtime floor is met

What it means. The installed runtime satisfies the floor this project's framework requires.

Why it matters. Nothing to do. Reported so a satisfied requirement is visible rather than inferred from the absence of a complaint.

How to fix it. No action needed.

next/runtime-too-old

A framework needs a newer runtime than this machine has

What it means. The framework this project depends on requires a runtime floor its own manifest does not state -- Next.js pins a Node version per major, Django pins a Python version, Spring Boot pins a JDK.

Why it matters. This is the case where every declared range is satisfied and the build still fails, because the requirement is one layer below the manifest. It also fails with a message that names something other than the cause: a syntax error rather than a Node version, a bytecode class-version number rather than a JDK.

How to fix it. Install a runtime at or above the floor named in the finding, and consider stating it in the project's own manifest -- engines in package.json, requires-python in pyproject.toml -- so the next person learns it from the file rather than from a build failure.

node-gyp/

node-gyp/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

node/

node/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

node/manager-conflict

Two version managers fighting over one ecosystem

What it means. More than one version manager for this ecosystem initialises in your shell profiles -- for example both nvm and fnm, or both conda and pyenv.

Why it matters. The last one to run wins, and which one that is depends on the order of lines in files you rarely read. The result is a tool version that changes when you open a different kind of terminal.

How to fix it. Pick one manager per ecosystem and remove the other's init lines from your shell profile. devrepro envmanagers shows what is declared and what is active.

node/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

node/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

node/shim-bypassed

A version manager is installed but not being used

What it means. The manager's shim directory is on PATH, but another installation of this tool resolves before it.

Why it matters. The manager still reports the version it intends -- pyenv version says 3.12 -- while every command gets something else, because resolution is decided by PATH order and nothing else. Neither tool is wrong about what it was asked, so nothing reports a problem, and the project's pinned version is quietly not in effect.

How to fix it. Move the manager's shim directory earlier in PATH than the installation that currently wins. devrepro which <tool> lists every candidate in precedence order. Note that an IDE's integrated terminal often has a different PATH from a login shell, so check the one you actually build in.

node/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

node/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

node/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

npm/

npm/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

nx/

nx/cache-credential-committed

A build-cache credential is in a committed configuration file

What it means. nx.json, turbo.json or .bazelrc sets a field that holds a remote-cache token or an Authorization header. The field's presence is reported; its value is never read.

Why it matters. A read-write cache credential is a supply-chain secret: whoever holds it can write cache entries that every developer and every CI run then treats as trusted build output, without any of them fetching the source it supposedly came from. These files get committed without a second thought because they read like configuration rather than like secrets -- .bazelrc especially, which looks like a flags file.

How to fix it. Move it to an environment variable, which all three tools read, and rotate it: it is in the git history whether or not you delete the line now.

openssl/

openssl/known-advisory

The installed tool version is covered by a published advisory

What it means. The version of this build tool matches an entry in the offline advisory set that ships with devrepro, or in the bundle you supplied with --db.

Why it matters. Dependency scanners never look at the compiler, the interpreter or git, because none of them appear in a lockfile. A toolchain can therefore sit years out of date behind a perfectly clean audit.

How to fix it. Upgrade the tool to the fix on its own release branch -- backported fixes mean the highest version number is not always the answer. This comparison is offline and does not know whether your distribution backported the fix into the version string you have, which many do; check your distribution's changelog before treating it as urgent.

path/

path/dead-entries

PATH entries that do not exist

What it means. PATH lists directories that are not present on disk.

Why it matters. The OS still stats every one of them on every lookup. On Windows in particular this measurably slows down each new process.

How to fix it. Remove the entries. If one was supposed to exist, the tool that owns it probably failed to install.

path/duplicates

Duplicate PATH entries

What it means. The same directory appears more than once in PATH.

Why it matters. Every duplicate is searched again on every command lookup, so process startup gets slower for no benefit. It is also a sign that a profile is appending to PATH each time it is sourced.

How to fix it. Remove the later occurrences, keeping the first. This never changes which executable wins, so it is a SAFE remediation.

path/store-aliases

Windows Store execution aliases on PATH

What it means. The WindowsApps alias directory is on PATH. It contains stub executables that open the Microsoft Store instead of running a tool.

Why it matters. The stubs commonly shadow real installations -- the classic symptom is python opening the Store rather than the Python you installed.

How to fix it. Settings > Apps > Advanced app settings > App execution aliases, and turn off the aliases for tools you have installed properly.

pip/

pip/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

ports/

ports/port-in-use

A declared port is already bound

What it means. A port the project declares is in use by another process.

Why it matters. The service will fail to start, usually with an 'address already in use' that does not say what is holding it.

How to fix it. Stop the process holding the port, or change the port the project declares.

psycopg2/

psycopg2/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

python/

python/known-advisory

The installed tool version is covered by a published advisory

What it means. The version of this build tool matches an entry in the offline advisory set that ships with devrepro, or in the bundle you supplied with --db.

Why it matters. Dependency scanners never look at the compiler, the interpreter or git, because none of them appear in a lockfile. A toolchain can therefore sit years out of date behind a perfectly clean audit.

How to fix it. Upgrade the tool to the fix on its own release branch -- backported fixes mean the highest version number is not always the answer. This comparison is offline and does not know whether your distribution backported the fix into the version string you have, which many do; check your distribution's changelog before treating it as urgent.

python/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

python/manager-conflict

Two version managers fighting over one ecosystem

What it means. More than one version manager for this ecosystem initialises in your shell profiles -- for example both nvm and fnm, or both conda and pyenv.

Why it matters. The last one to run wins, and which one that is depends on the order of lines in files you rarely read. The result is a tool version that changes when you open a different kind of terminal.

How to fix it. Pick one manager per ecosystem and remove the other's init lines from your shell profile. devrepro envmanagers shows what is declared and what is active.

python/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

python/multiple-installations

Several copies of the same tool on PATH

What it means. More than one executable with this name resolves on PATH. The first wins, and the others are reachable only by full path.

Why it matters. The one that wins depends on PATH order, which differs between your shell, your editor's terminal, and CI. That is how the same command produces different versions in different windows on one machine.

How to fix it. Run devrepro which <tool> to see every candidate and which one wins. Keep the installation you intend to use and remove or de-prefer the rest; devrepro plan proposes the PATH edit.

python/multiple-versions

Several Python versions installed

What it means. More than one Python interpreter is present with differing versions.

Why it matters. Not a problem in itself -- it is normal and often deliberate. It is reported because it is the context you need when a package installs into an interpreter other than the one you are running.

How to fix it. No action needed unless a requirement is unmet. Use a per-project version manager or a virtualenv to make the choice explicit.

python/shim-bypassed

A version manager is installed but not being used

What it means. The manager's shim directory is on PATH, but another installation of this tool resolves before it.

Why it matters. The manager still reports the version it intends -- pyenv version says 3.12 -- while every command gets something else, because resolution is decided by PATH order and nothing else. Neither tool is wrong about what it was asked, so nothing reports a problem, and the project's pinned version is quietly not in effect.

How to fix it. Move the manager's shim directory earlier in PATH than the installation that currently wins. devrepro which <tool> lists every candidate in precedence order. Note that an IDE's integrated terminal often has a different PATH from a login shell, so check the one you actually build in.

python/store-alias-shadow

A Store alias is shadowing a real Python

What it means. A WindowsApps python stub resolves before a genuine Python installation.

Why it matters. python will not run the interpreter you installed. Virtualenv creation, pip and every script fail in ways that do not mention the alias.

How to fix it. Disable the python app execution alias, or move the real installation's directory earlier in PATH.

python/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

python/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

python/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

ruby/

ruby/shim-bypassed

A version manager is installed but not being used

What it means. The manager's shim directory is on PATH, but another installation of this tool resolves before it.

Why it matters. The manager still reports the version it intends -- pyenv version says 3.12 -- while every command gets something else, because resolution is decided by PATH order and nothing else. Neither tool is wrong about what it was asked, so nothing reports a problem, and the project's pinned version is quietly not in effect.

How to fix it. Move the manager's shim directory earlier in PATH than the installation that currently wins. devrepro which <tool> lists every candidate in precedence order. Note that an IDE's integrated terminal often has a different PATH from a login shell, so check the one you actually build in.

rust/

rust/known-bad-version

Version explicitly forbidden by policy

What it means. The installed version matches a range listed under [known_bad_versions] in the project's .devrepro.toml.

Why it matters. Someone recorded that this exact version breaks the project. That is more specific than a range check and usually earned the hard way.

How to fix it. Move off the forbidden version. The policy file should say why; if it does not, add the reason for whoever hits it next.

rust/missing

Required tool not found

What it means. The project declares this tool as a requirement and it does not resolve on PATH.

Why it matters. Any command that needs it fails immediately, usually with a confusing 'not recognized' or 'command not found' rather than a note about the declared requirement.

How to fix it. Install it, or remove the requirement from the manifest if it is no longer real. Check devrepro which <tool> first -- the tool may be installed but shadowed or off PATH in this shell.

rust/version-mismatch

Version outside the declared range

What it means. The tool is installed, but its version does not satisfy what the project's manifest requires.

Why it matters. This is the most common cause of a build that works for one person and not another. Lockfiles, syntax features and native modules are all version-sensitive, and the failure usually surfaces far from the cause.

How to fix it. Install a version inside the declared range, or widen the range if the declaration is stale. A version manager (mise, asdf, nvm, pyenv) makes this per-project rather than global.

rust/version-ok

Version satisfies the requirement

What it means. The installed version falls inside the range the project declares.

Why it matters. Nothing to do. It is reported so a passing check is visible rather than inferred from silence.

How to fix it. No action needed.

rust/version-unparseable

Version string could not be read

What it means. The tool responded, but its version output did not match any pattern this project knows how to parse.

Why it matters. The requirement cannot be checked either way, so this is reported as unknown rather than passing. A silent pass here would be a lie.

How to fix it. Run the tool's version command by hand and open an issue with the output, so the parser can learn the shape.

sandbox/

sandbox/cpu-parity

The sandbox gets fewer cores than the host, and build tools will not notice

What it means. The effective core count inside the sandbox is below the host's.

Why it matters. Build tools that detect parallelism through nproc, os.cpu_count() or an older JVM read the host's number and spawn that many workers into a smaller box. Nothing fails: the build thrashes and finishes several times slower, with no log line anywhere saying why.

How to fix it. Pin the parallelism explicitly -- make -j, cargo build -j, CARGO_BUILD_JOBS, MAKEFLAGS -- rather than letting the tool detect it.

sandbox/memory-parity

The sandbox gets far less memory than the machine it was tested on

What it means. The container engine's ceiling, or a limit declared in compose or a devcontainer, is under a quarter of the host's memory.

Why it matters. A build that links comfortably here can be killed in the sandbox with exit code 137 -- that is 128 plus SIGKILL, sent by the kernel's OOM killer, which writes nothing to the build log. It reads as a compiler crash, and the fix people reach for is a compiler flag.

How to fix it. Raise the engine's memory limit (Docker Desktop: Settings > Resources), or lower the build's peak by pinning its parallelism. Plenty of containers are deliberately smaller than their host, so this is a difference worth knowing rather than an error.

sandbox/network-parity

The sandbox has no network and the build fetches dependencies

What it means. A compose file or devcontainer disables the network, and this project's setup needs to reach a registry.

Why it matters. No network is the correct default for an agent sandbox and the wrong one for a first build. Both declarations live in the same repository and neither knows about the other.

How to fix it. Warm the dependency cache in an image layer, or vendor the dependencies, so the isolated run needs nothing from outside.

sharp/

sharp/needs-toolchain

A declared dependency compiles from source on this machine

What it means. The project declares a package whose installation needs a compiler, a client library or a system dependency -- psycopg2, mysqlclient, sharp, canvas and their relatives.

Why it matters. Reported as information rather than a problem: a machine with a working toolchain, or one where a prebuilt binary matches, installs it without noticing. It matters when neither is true, and then the failure is a wall of compiler output that names a header file. Note psycopg2 and psycopg2-binary are one character apart and land on opposite sides of this.

How to fix it. Either install what the finding names, or switch to the prebuilt variant where one exists. On a container base image this is usually the difference between a five-second install and a ten-minute one.

shell/

shell/managers-initialized

Version managers initialised by shell profiles

What it means. Which tool managers your shell profiles set up at startup.

Why it matters. Context for PATH ordering and for manager-conflict.

How to fix it. No action needed.

shell/slow-startup

A shell profile runs several subshell-spawning initialisations

What it means. Four or more version managers or prompt tools initialise in a profile file, each forking at least one process before the prompt appears.

Why it matters. Every new terminal pays this, and so does every git hook that spawns a login shell and every bash -lc in CI. Four of them together is one to three seconds, and nobody attributes it -- a shell that takes two seconds reads as a slow machine.

How to fix it. Most of these support lazy initialisation: a shim that runs the real init the first time the tool is called, costing nothing until then. This is a count rather than a measurement, because timing a shell start means running your own configuration, which is not a read-only thing for a diagnostic to do.

spring-boot/

spring-boot/runtime-missing

A framework needs a runtime that does not resolve here

What it means. The project depends on a framework requiring a runtime, and that runtime is not on PATH at all.

Why it matters. Nothing about this project will build. Reported separately from a version mismatch because the fix is different: one is an upgrade, the other is an install -- or a PATH problem, which devrepro which answers.

How to fix it. Install the runtime, then check devrepro which <tool>: it is often installed and shadowed, which looks identical from here.

spring-boot/runtime-ok

The framework's runtime floor is met

What it means. The installed runtime satisfies the floor this project's framework requires.

Why it matters. Nothing to do. Reported so a satisfied requirement is visible rather than inferred from the absence of a complaint.

How to fix it. No action needed.

spring-boot/runtime-too-old

A framework needs a newer runtime than this machine has

What it means. The framework this project depends on requires a runtime floor its own manifest does not state -- Next.js pins a Node version per major, Django pins a Python version, Spring Boot pins a JDK.

Why it matters. This is the case where every declared range is satisfied and the build still fails, because the requirement is one layer below the manifest. It also fails with a message that names something other than the cause: a syntax error rather than a Node version, a bytecode class-version number rather than a JDK.

How to fix it. Install a runtime at or above the floor named in the finding, and consider stating it in the project's own manifest -- engines in package.json, requires-python in pyproject.toml -- so the next person learns it from the file rather than from a build failure.

system/

system/os-detected

Operating system detected

What it means. The OS, version and architecture this scan ran on.

Why it matters. Every other finding is relative to this. It is also the first thing anyone comparing two machines wants.

How to fix it. No action needed.

system/resources

CPU, memory and disk headroom

What it means. Totals only -- no serial numbers, no SMART data.

Why it matters. Builds fail in confusing ways when a disk is nearly full, and a container build can exhaust one quietly.

How to fix it. Free space if the report shows little headroom.

system/shell

Active shell

What it means. Which shell this scan believes you are running.

Why it matters. Determines which profile files matter for PATH and manager initialisation.

How to fix it. No action needed.

turborepo/

turborepo/cache-credential-committed

A build-cache credential is in a committed configuration file

What it means. nx.json, turbo.json or .bazelrc sets a field that holds a remote-cache token or an Authorization header. The field's presence is reported; its value is never read.

Why it matters. A read-write cache credential is a supply-chain secret: whoever holds it can write cache entries that every developer and every CI run then treats as trusted build output, without any of them fetching the source it supposedly came from. These files get committed without a second thought because they read like configuration rather than like secrets -- .bazelrc especially, which looks like a flags file.

How to fix it. Move it to an environment variable, which all three tools read, and rotate it: it is in the git history whether or not you delete the line now.

virt/

virt/status

Virtualization capability

What it means. Whether hardware virtualization and the relevant hypervisor are available.

Why it matters. WSL2 and container backends need it. It is often disabled in firmware on new machines.

How to fix it. Enable virtualization in firmware if a container backend needs it.

wsl/

wsl/detected

WSL is available

What it means. WSL was found, with its distributions listed.

Why it matters. Recorded because a Windows machine with WSL behaves very differently from one without, and the default distro determines which filesystem commands run against.

How to fix it. No action needed.

wsl/interop-disabled

WSL interop is disabled

What it means. Windows/Linux interop is turned off in this WSL installation.

Why it matters. Calling Windows executables from inside WSL fails, which breaks many cross-platform toolchains.

How to fix it. Enable interop in /etc/wsl.conf and restart WSL.

wsl/no-default-distro

WSL has no default distribution

What it means. WSL is installed but no distribution is set as default.

Why it matters. wsl <command> fails, and tools that shell into WSL fail with it.

How to fix it. wsl --set-default <distro>.

wsl/not-installed

WSL is not installed

What it means. No WSL installation was detected on this Windows machine.

Why it matters. Matters only if the project expects a Linux environment.

How to fix it. wsl --install if the project needs it.