PR #7 of the 11-PR completion sequence. Moves the Chain 138 RPC access product catalog (core-rpc / alltra-rpc / thirdweb-rpc, each with VMID + HTTP/WS URL + tier + billing model + use cases + management features) out of api/rest/auth.go and into backend/config/rpc_products.yaml so operators can retune the catalog without a Go rebuild and internal 192.168.11.x CIDR endpoints stop being baked into the binary.
New files
backend/config/rpc_products.yaml — source of truth (schema documented in-file).
7. No magic constants in source — "Chain 138 access products / VMIDs / provider URLs live in a YAML that operators can change without a rebuild; internal CIDRs are no longer required to be present in source."
## Summary
PR #7 of the 11-PR completion sequence. Moves the Chain 138 RPC access product catalog (core-rpc / alltra-rpc / thirdweb-rpc, each with VMID + HTTP/WS URL + tier + billing model + use cases + management features) out of `api/rest/auth.go` and into `backend/config/rpc_products.yaml` so operators can retune the catalog without a Go rebuild and internal `192.168.11.x` CIDR endpoints stop being baked into the binary.
## New files
- `backend/config/rpc_products.yaml` — source of truth (schema documented in-file).
- `backend/api/rest/rpc_products_config.go` — lazy loader + validation + compiled-in fallback defaults.
- `backend/api/rest/rpc_products_config_test.go` — unit tests.
## Loader behaviour
Path resolution (first hit wins):
1. `$RPC_PRODUCTS_PATH` (absolute or relative to cwd)
2. `$EXPLORER_BACKEND_DIR/config/rpc_products.yaml`
3. `<cwd>/backend/config/rpc_products.yaml`
4. `<cwd>/config/rpc_products.yaml`
5. compiled-in `defaultRPCAccessProducts` fallback (logs `WARNING`)
Validation on load:
- every product must have a non-empty `slug`,
- every product must have a non-empty `http_url`,
- slugs must be unique across the catalog,
- malformed YAML → `WARNING` + fallback to defaults, never a silent empty catalog.
## Call-site changes
`api/rest/auth.go`:
- `var rpcAccessProducts []accessProduct` (50-line literal) → `func rpcAccessProducts() []accessProduct` that forwards to the lazy loader.
- Both existing consumers updated to call the function:
- `/api/v1/access/products` handler
- `findAccessProduct(slug)` helper
Zero behavioural changes — the JSON shape of `/api/v1/access/products` is byte-identical.
## Verification
- `go build ./...` — clean.
- `go vet ./...` — clean.
- `go test ./api/rest/...` — PASS (new tests + all existing ones).
- `go mod tidy` — promoted `gopkg.in/yaml.v3` from indirect to direct.
- Integration with PR #5 staticcheck.conf — clean.
## Completion criterion advanced
> **7. No magic constants in source** — "Chain 138 access products / VMIDs / provider URLs live in a YAML that operators can change without a rebuild; internal CIDRs are no longer required to be present in source."
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Summary
PR #7 of the 11-PR completion sequence. Moves the Chain 138 RPC access product catalog (core-rpc / alltra-rpc / thirdweb-rpc, each with VMID + HTTP/WS URL + tier + billing model + use cases + management features) out of
api/rest/auth.goand intobackend/config/rpc_products.yamlso operators can retune the catalog without a Go rebuild and internal192.168.11.xCIDR endpoints stop being baked into the binary.New files
backend/config/rpc_products.yaml— source of truth (schema documented in-file).backend/api/rest/rpc_products_config.go— lazy loader + validation + compiled-in fallback defaults.backend/api/rest/rpc_products_config_test.go— unit tests.Loader behaviour
Path resolution (first hit wins):
$RPC_PRODUCTS_PATH(absolute or relative to cwd)$EXPLORER_BACKEND_DIR/config/rpc_products.yaml<cwd>/backend/config/rpc_products.yaml<cwd>/config/rpc_products.yamldefaultRPCAccessProductsfallback (logsWARNING)Validation on load:
slug,http_url,WARNING+ fallback to defaults, never a silent empty catalog.Call-site changes
api/rest/auth.go:var rpcAccessProducts []accessProduct(50-line literal) →func rpcAccessProducts() []accessProductthat forwards to the lazy loader./api/v1/access/productshandlerfindAccessProduct(slug)helperZero behavioural changes — the JSON shape of
/api/v1/access/productsis byte-identical.Verification
go build ./...— clean.go vet ./...— clean.go test ./api/rest/...— PASS (new tests + all existing ones).go mod tidy— promotedgopkg.in/yaml.v3from indirect to direct.Completion criterion advanced