Skip to content

docs: name the forge-std prerequisite in the README Install section - #117

Closed
thedavidmeister wants to merge 4 commits into
mainfrom
2026-08-16-issue-82
Closed

docs: name the forge-std prerequisite in the README Install section#117
thedavidmeister wants to merge 4 commits into
mainfrom
2026-08-16-issue-82

Conversation

@thedavidmeister

@thedavidmeister thedavidmeister commented Aug 16, 2026

Copy link
Copy Markdown
Contributor

Closes #82

What a consumer actually needs

  • forge-std version: 1.16.1 — the pin in foundry.toml [dependencies],
    matching soldeer.lock. Stale soldeer pin: foundry.toml pins forge-std 1.16.1 with 1.16.2 published, and the version is baked into every import prefix #90 owns whether that pin is stale; this PR documents
    what is pinned today and does not move it.
  • Import prefix: forge-std-1.16.1/src/lib/LibCodeGen.sol:5,
    src/lib/LibFs.sol:5 and src/lib/LibHexString.sol:5 each import
    forge-std-1.16.1/src/Vm.sol. forge soldeer install forge-std~1.16.1 in the
    consuming project writes exactly
    forge-std-1.16.1/=dependencies/forge-std-1.16.1/ to remappings.txt, which
    is what makes the prefix resolve.

The issue's conclusion, re-derived

The issue concluded the README is the place to fix this, on the grounds that a
sibling package ships no foundry.toml either, so shipping none is convention.
I checked that and then checked whether the package route could work at all.

rain-math-float~0.1.7 does ship no foundry.toml, soldeer.lock or
remappings.txt — confirmed against the published zip. But "sibling does the
same" is a weaker argument than the mechanism, so I measured the mechanism.

Reproduced the consumer failure against the published package in a scratch
foundry project (rain-sol-codegen~0.1.12, 21 zip entries, none of them
foundry.toml/soldeer.lock/remappings.txt):

$ forge soldeer install    # rain-sol-codegen only
$ cat remappings.txt
rain-sol-codegen-0.1.12/=dependencies/rain-sol-codegen-0.1.12/
$ forge build
Error (6275): Source "forge-std-1.16.1/src/Vm.sol" not found: File not found.
 --> dependencies/rain-sol-codegen-0.1.12/src/lib/LibCodeGen.sol:5:1

Then confirmed the documented prerequisite is sufficient:

$ forge soldeer install forge-std~1.16.1
$ cat remappings.txt
forge-std-1.16.1/=dependencies/forge-std-1.16.1/
rain-sol-codegen-0.1.12/=dependencies/rain-sol-codegen-0.1.12/
$ forge build
Compiler run successful!

Then tested the package route directly, by hand-building the exact tree a
recursive soldeer install would produce — forge-std under
dependencies/rain-sol-codegen-0.1.12/dependencies/forge-std-1.16.1/, plus a
remappings.txt inside the dependency directory naming the prefix:

$ forge remappings
rain-sol-codegen-0.1.12/=dependencies/rain-sol-codegen-0.1.12/
$ forge build
Error (6275): Source "forge-std-1.16.1/src/Vm.sol" not found: File not found.

A dependency's own remappings.txt is not consulted; only the consuming
project's root remappings count, and soldeer writes those only for direct
dependencies. forge soldeer install --help also confirms --recursive-deps /
[soldeer] recursive_deps is a flag in the consuming project, off by
default (this repo sets it false explicitly) — so a package-side manifest
could not guarantee resolution even if it were shipped.

So the conclusion holds, on a stronger basis than convention: there is no
package-side artifact that can supply this prefix. The README is the only place
it can live, and the README is shipped in the published zip, so the
prerequisite reaches the consumer either way.

Change

  • README.md (+16) — the Install section now names the version, the prefix, the
    install command, the remapping it generates, and the compiler error you get
    without it.

That is the entire diff. No test, and foundry.toml is byte-identical to main.

No test guards this, and it can regress silently

This change is guarded by nothing. If someone bumps [dependencies] forge-std in foundry.toml — which #90 is open to do — the README will keep
naming 1.16.1 and forge-std-1.16.1/, the suite will stay green, and every
consumer following the Install section will install the wrong forge-std and hit
exactly the Source "forge-std-1.16.1/src/Vm.sol" not found compile error this
section exists to prevent. The same is true of any later README edit that drops
or rewords the paragraph. The regression is silent in CI and only surfaces in a
downstream project.

That is deliberate, and it replaces an earlier version of this PR. This PR
originally shipped test/README.t.sol (37 lines) plus a { access = "read", path = "README.md" } fs_permissions grant. Both are removed here. The
check is rehomed to rainlanguage/rainix#317, which collects the six
hand-rolled Solidity static-analysis harnesses this fleet produced and asks for
them as rainix-static subcommands in Rust, with bats coverage, inherited by
every consumer through the rainix reusables instead of copied per repo.

Cause, stated plainly: the fixer brief driving this fleet said "every fix ships
a test, verify-by-hand is never acceptable", with no exemption for changes that
have no behaviour. That instruction was wrong and has been corrected. A README
paragraph has no behaviour, and the test it forced was a bad check on its own
terms — its subject was a TOML file and a markdown file, not any code in src/,
and vm.contains on prose passes if the string appears anywhere in the file.
It could not establish that the Install section is correct, only that two
substrings exist somewhere in the README. What it actually did was fight the
next README edit.

Note for #90 supersedes the one this PR carried before: bumping the forge-std
pin no longer fails anything here. Whoever does it has to update this README
paragraph by hand, or wait for the rainix#317 check to land.

QA

Full suite and formatting from the flake shell (nix develop -c), on the merge
commit before and after the strip:

before: Ran 19 test suites in 2.06s (21.86s CPU time): 144 tests passed, 0 failed, 0 skipped (144 total tests)
after:  Ran 18 test suites in 3.37s (32.60s CPU time): 142 tests passed, 0 failed, 0 skipped (142 total tests)

$ forge fmt --check
fmt-exit=0

(Wall/CPU differ between the two runs only because the machine was running
other builds concurrently; the pass/fail counts are the measurement.)

144 → 142 is exactly the two functions in the deleted test/README.t.sol
(testReadmeNamesPinnedForgeStdVersion, testReadmeNamesForgeStdImportPrefix);
19 → 18 suites is that file's ReadmeTest contract. Nothing else moved.


Post-Build.sol-removal sweep (2026-08-17)

main (959d527) merged in. Unaffected by #138's removal of
script/Build.sol — this PR is one paragraph in the Install section and touches
nothing the removal deleted. Nothing cut.

Re-verified against main rather than restated:

Coupled to #126. #126 bumps forge-std 1.16.11.16.2 and rewrites that
import prefix. Whichever of the two lands second has to carry the other's
version: if #126 lands first, the three 1.16.1 strings added here become
1.16.2. Stated rather than pre-applied, because main is on 1.16.1 today and
a README that names a version the source does not import would be wrong now
instead of later.

Suite on the merge commit: Ran 19 test suites: 145 tests passed, 0 failed, 0 skipped (145 total tests). forge fmt --check clean, git status clean after
the run.

The published package ships no foundry.toml, soldeer.lock or remappings.txt,
and soldeer writes remappings only for a project's own direct dependencies, so
a consumer gets an unresolvable `forge-std-1.16.1/src/Vm.sol` import the moment
they import anything from this package. State the version and the prefix as an
install prerequisite, and pin the claim to foundry.toml with a test.

Closes #82

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@thedavidmeister thedavidmeister self-assigned this Aug 16, 2026
@coderabbitai

coderabbitai Bot commented Aug 16, 2026

Copy link
Copy Markdown

Warning

Review limit reached

@thedavidmeister, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 59 minutes

Limit details: You’ve used all 1 included review currently available under your plan.

You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository.

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: fb02ab96-bb14-4bd6-901a-b005bc192b82

📥 Commits

Reviewing files that changed from the base of the PR and between 959d527 and 8db8878.

📒 Files selected for processing (1)
  • README.md

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

thedavidmeister and others added 3 commits August 16, 2026 19:20
Delete `test/README.t.sol` and revert the `{ access = "read", path =
"README.md" }` `fs_permissions` grant it needed. The README Install section
edit — the actual fix for #82 — is unchanged.

The deleted test's subject was a TOML file and a markdown file, not any code in
`src/`. `vm.contains` on prose passes if the substring appears anywhere in the
file, so it could not establish that the Install section is correct; it only
stood in the way of the next README edit. The check is rehomed to
rainlanguage/rainix#317 as a `rainix-static` subcommand.

`foundry.toml` is now byte-identical to `main`.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@thedavidmeister

Copy link
Copy Markdown
Contributor Author

Closing: this documents how soldeer works, which is not this README's subject.

Every fact the added section carries is a property of soldeer, identical for
every package soldeer serves:

  • that it writes versioned remapping prefixes,
  • that forge soldeer install forge-std~1.16.1 produces
    forge-std-1.16.1/=dependencies/forge-std-1.16.1/,
  • that a missing prefix fails as Source "..." not found,
  • that a forge-std obtained another way needs the prefix mapped by hand.

None of it is specific to rain-sol-codegen. Restating it here makes this repo
one of N copies of soldeer's own documentation, and a copy that goes stale
independently of the tool it describes.

It is also unnecessary, by the mechanism this PR's own text quotes. Soldeer's
versioned prefixes mean the import is the dependency declaration, carried in
the source where it cannot drift from the source. A consumer without forge-std
gets Source "forge-std-1.16.1/src/Vm.sol" not found, which maps one-to-one
onto forge soldeer install forge-std~1.16.1. The compiler names the version
because the version is in the prefix.

The prose is the copy that rots. #126 bumps forge-std to 1.16.2 and does not
touch README.md, so the moment both land this section names a version nothing
imports while the compiler keeps naming the right one.

#82 is closed with the same reasoning.

The branch is left in place as the audit trail.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

The published rain-sol-codegen package ships no dependency metadata, and the README never names the forge-std version its imports require

2 participants