You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Fixes#9631. Cached task keys ignored the metabuild classpath, so plugin version changes replayed stale values and poisoned CachedCompileFailure entries until cleanFull. Adds a metabuild classpath digest to every key and keys cached failures on the full build definition. Includes scripted regression test.
The action cache key for a cached task is sha256(codeContentHash, hash(inputs), extraHash, cacheVersion), where codeContentHash is the hash of the task body's macro tree (Cont.scala) and extraHash is always 0. Nothing in the key reflects the metabuild classpath. A plugin like sbt-scalac-opts-plugin defines scalacOptions ++= scalacOptsFor(scalaVersion.value, scalacOptsAll) — the tree is identical across plugin versions, only the data behind it changes. So after a version bump:
scalacOptions (and compile) replayed stale cached values;
after cleanFull, a recompile with the stale options failed and the CachedCompileFailure was recorded under a key that ignores the plugin classpath;
every subsequent compile replayed that failure for a configuration that compiles fine; only cleanFull recovered.
How it's fixed
On each project load, two digests are computed from already-available content hashes and passed via BuildWideCacheConfiguration:
metaBuildDigest: every build unit's pluginData.classpath (plugin/dependency jars + compiled project/*.scala products). Mixed into every cached task key, so any plugin or build-helper change invalidates dependent cached values.
buildDefinitionDigest: the above plus the Eval-generated .sbt classes. Used only to key cached failures: a failure is stored under sha256(inputDigest, buildDefinitionDigest) and can only replay while the whole build definition is byte-identical. Failure entries written by older sbt under the loose key are treated as a miss and overwritten.
The .sbt dsl classes are deliberately excluded from the global key so a plain build.sbt edit doesn't invalidate the entire cache (guarded by the existing cache/version-bump-compile scripted test).
Verified with the repro from https://github.com/stasimus/sbt2-stale-cache-repro: all README steps produce the expected exit codes with this patch. New scripted test cache/plugin-scalac-options-toggle covers the toggle scenario; utilCache/test, scripted cache/*, and MiMa all pass.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #9631. Cached task keys ignored the metabuild classpath, so plugin version changes replayed stale values and poisoned CachedCompileFailure entries until cleanFull. Adds a metabuild classpath digest to every key and keys cached failures on the full build definition. Includes scripted regression test.