Skip to content

ci: make Go Checks, Go Test and Build green again - #252

Merged
ehsan6sha merged 5 commits into
mainfrom
ci/green
Oct 8, 2026
Merged

ehsan6sha merged 5 commits into
mainfrom
ci/green

Conversation

@ehsan6sha

Copy link
Copy Markdown
Member

Why

All three CI checks were red on main for reasons unrelated to the code they check, so the two required ones (unit, All) had stopped gating anything:

Check Cause
Go Checks / All staticcheck v0.4.6 doesn't build on Go 1.25 (since 2026-02), and shadow@latest now needs Go 1.26, so neither staticcheck nor the blocking wap/pkg/server shadow gate ran. gofmt flagged 9 files.
Go Test / unit A port collision between two tests on fixed 0.0.0.0:4020/4021; a "mock server" test that never reached its mock (hard-coded RPC URLs); live-chain tests with stale expectations; obsolete examples panicking. The -race step never ran, and once it does it finds 4 data races in the lanbind tests.
Build / Container The root Dockerfile is a stale copy of fula-ota's (COPYs files that don't exist here). Release images come from fula-ota's Dockerfile.

None of these is a bug in what devices run. One real but latent issue is fixed here: nil pool/chain getters passed to the blockchain options replaced the safe defaults (the daemon always sets them, so it never triggered).

What changes (one commit per step)

  1. gofmt — whitespace only.
  2. Go Checks — pin [email protected] and [email protected] (the last releases that build on Go 1.25; cmd/blox doesn't build on 1.26 yet) and fix all 113 staticcheck findings:
    • WithUseTransient → WithAllowLimitedConn (identical in go-libp2p v0.47.0: same context key).
    • ImageInspectWithRaw → ImageInspect.
    • Unused values, dead code and simplifications. Each behaviour-relevant case is listed in the commit message.
    • Three unused kubo HTTP-API helpers in cmd/blox stay behind //lint:ignore. Removing them would drop ~250 packages and their init()s (e.g. dag-jose/git codec registration) from the daemon; that deserves its own change.
  3. Tests — test-only hooks for listen addresses and chain configs (unexported; defaults unchanged and pinned by a test). The mock-server test now really uses its mock. Live-chain tests move behind the existing livechain tag (go test -tags livechain ./blockchain/). Obsolete examples are removed. Nil getters now keep the defaults.
  4. WAP race — multiCloser.Close() waits for the hotspot/LAN watchers after releasing its lock (they exit within one tick once closed), and the tests stop swapping config paths under a running watcher. The race step gets -timeout 20m: mobile's tests spend ~5 min waiting out fixed client timeouts.
  5. Container — remove build.yml, publish.yml (its only job pushed that image to GHCR and has failed on every release since 2025-06) and the root Dockerfile.

Daemon behaviour

  • cmd/blox, wap/cmd and modules/initipfscluster (linux/arm64) link exactly the same packages as main.
  • modules/initipfs no longer links stdlib net/http; its only user was dead code.
  • go.mod/go.sum are unchanged.
  • Listen addresses, chain configs and option defaults are unchanged.
  • The only runtime difference is that WAP's server Close() returns once its watchers have stopped, instead of immediately.

Verification (Go 1.25.14, the pinned tools, GOTOOLCHAIN=local)

  • Go Checks sequence, in CI's order, passes: go mod tidy (no diff), gofmt -s, go vet, blocking shadow, staticcheck, go generate (no diff). vet and staticcheck with -tags livechain are clean too.
  • Go Test: go test -v -shuffle=on ./... passes ×2, and go test -v -race -timeout 20m ./... passes ×2 with no data races (on main the race step finds 4).
  • No internet (network namespace with only loopback): everything passes except TestMDNSServiceDiscovery. mDNS needs a non-loopback interface, which runners have.
  • Live chains: go test -tags livechain ./blockchain/ passes 8 tests (read-only, real SKALE and Base contracts).
  • Binaries: cmd/blox, wap/cmd, modules/initipfs and modules/initipfscluster build for linux/arm64, and go list -deps is identical to main apart from initipfs no longer linking net/http.
  • Review: an independent review (Antigravity) of all 5 commits found no issues, including in the multiCloser wait (no deadlock or WaitGroup misuse) and the daemon defaults.

Release order

Suggest cutting the fula-ota release from main before merging this, so the pool-leave release (#251) ships on its own and this goes out in the next one.

🤖 Generated with Claude Code

https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx

ehsan6sha and others added 5 commits October 8, 2026 12:04
Whitespace only (`git diff -w` shows one removed blank line). The gofmt
step of the required "Go Checks / All" job fails on these nine files.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx
The required "Go Checks / All" job has not run staticcheck since
February: v0.4.6 doesn't build on Go 1.25, and `shadow@latest` now
needs Go 1.26, so the blocking shadow gate for wap/pkg/server stopped
running too. Pin staticcheck v0.7.0 (2026.1) and x/tools v0.49.0, the
last releases that build on Go 1.25 (cmd/blox doesn't build on 1.26
yet), and fix what staticcheck v0.7.0 reports (113 findings):

- SA1019: network.WithUseTransient -> WithAllowLimitedConn (64 calls;
  in go-libp2p v0.47.0 both set the same context key);
  docker ImageInspectWithRaw -> ImageInspect (same struct, the unused
  raw bytes dropped).
- SA4006 in the daemon (blockchain/blox.go, 4 handlers): `out := T{..}`
  was overwritten on every path; now `var out T`. Same response.
- SA4006 in tests (13): calls whose errors the tests deliberately
  ignore keep the call, as `_ = f()`.
- SA4017 (blox/kubo_proxy.go): removed an `if` whose body was only a
  "no-op" comment; its conditions are side-effect free.
- U1000: removed unused functions and fields in blockchain, blox,
  cmd/blox (updateConfig), modules/initipfs (+ the commented-out call)
  and wap/pkg/server. The three unused kubo HTTP-API helpers in
  cmd/blox stay, behind lint:ignore: they are the only importer of
  kubo's commands/corehttp stack, and removing them would drop ~250
  packages and their init()s (e.g. dag-jose and git codec registration)
  from the daemon. cmd/blox links exactly the same packages as before
  and go.mod/go.sum are unchanged.
- S1017/S1031/S1039: TrimPrefix, a nil check around range, and a
  test init() that did nothing.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx
…ffline

Go Test / unit failed on every run for reasons outside the code under
test:

- TestFxBlockchainCreation / TestBlockchainHealthCheck both Start() the
  proxy and ping servers on the fixed 0.0.0.0:4020/4021 and never shut
  down, so whichever ran second failed to bind. FxBlockchain gets
  unexported withListenAddrs (tests use 127.0.0.1:0) and the tests shut
  down via t.Cleanup.
- TestPoolDiscoveryWithMockServer never reached its mock: callEVMChain
  always used the hard-coded RPC URLs, so it asserted live chain state.
  Chain configs now go through bl.chainConfigs(), which tests can
  replace with the unexported withChainConfigs; the mock answers
  poolIds(0), reports problems with t.Errorf instead of require on the
  server goroutine, and compares addresses case-insensitively.
- Tests that need the real SKALE/Base contracts (integration_test.go,
  pool_bug_test.go, two pool discovery tests) move behind the existing
  `livechain` build tag, with their stale expectations fixed (Base's
  pool 1 is Global-B1; the decoder returns lowercase addresses).
  `go test -tags livechain ./blockchain/` runs them.
- exchange/example_test.go: both examples exercised Pull/Push, which now
  return "no longer supported", and panicked on a nil chain getter.
  Removed with their helpers.

Robustness: blockchain.With{Get,Update}{Pool,Chain}Name ignore nil and
keep their defaults (blox.New passes its options through even when they
were never set), and blox guards its own getPoolName call. The daemon
always sets all four, and the defaults are unchanged: a new test pins
0.0.0.0:4020/4021, GetChainConfigs() and the nil handling.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx
…races

The -race step of Go Test never ran in CI (the step before it always
failed), and it fails in wap/pkg/server: 4 data races in 3 lanbind
tests. multiCloser.Close() stopped the hotspot / LAN-setup watchers but
did not wait for them, so a test restoring a package setting
(hotspotWatchInterval, lanWatchInterval, lanListenAddrs) raced with a
watcher still reading it.

- multiCloser counts its watchers (trackWatcher, under mu, so it can't
  race Close); Close() closes listeners and stopWatch under mu, then
  releases mu and waits. Waiting under mu would deadlock against a
  watcher in add(); with `closed` set add() refuses and the watcher
  returns, so the wait is at most one tick. Callers see the same
  result as before, slightly later.
- TestLANSetupWatchStopsOnceTheBloxHasAnOwner swapped
  config.FULA_CONFIG_PATH while the watcher read it; it now rewrites
  the same file atomically (claimConfig).

Go Test's race step gets -timeout 20m: mobile's client tests spend ~5
min waiting out the client's fixed dial timeouts and took 516 s of the
default 600 s under -race locally.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx
The root Dockerfile is an old copy of fula-ota's: it COPYs ./go-fula/
and ./go-fula.sh, which don't exist in this repo, so "Build / Container"
has failed on every push since 2025-06-11, and publish.yml (its only job
pushes that image to GHCR on release) has failed on every release.
Release images are built from fula-ota's Dockerfile and pushed to Docker
Hub; nothing else in this repo references these files.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01QaKz9HeXaNBjrchbbGimFx
@ehsan6sha
ehsan6sha merged commit 51ccb3e into main Oct 8, 2026
7 checks passed
@ehsan6sha
ehsan6sha deleted the ci/green branch October 8, 2026 17:21
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.

1 participant