# Build the project
go build ./...
# Run go vet checks
go vet ./...
# Run tests (note: no test files exist yet)
go test ./...
# Format
gofmt -w .
# Update dependencies
go get -u ./...
go mod tidy- ALWAYS Use
gofmtafter finish creating/editing a Golang file once you are ready to run tests or make any other external validations but after it compiles correctly.
- Main package: root directory
- Commands:
cmd/sf_analyzer/andcmd/sf_comparator/ - Metrics:
metrics/
- Go Version: 1.24.0 (toolchain go1.24.4)
- Build Status: PASSING
- Test Status: PASSING (21 tests)
- Only use latest Golang features instead of older idioms (slices, maps, iter, any, generics, etc.)
When parsing CLI flags that require validation:
- Use
cli.Ensurefor required field presence checks (preferred) - Use non-Must parsing functions and handle errors with
cli.NoError - Provide contextual error messages - adjust based on whether field is required or optional
// Preferred - check required fields with cli.Ensure
cli.Ensure(signerKeyHex != "", "<signer-key> is required")
// Good - parsing with contextual error for required field
addr, err := parseAddress(addrHex)
cli.NoError(err, "invalid <service-provider> address %q, it is required", addrHex)
// Good - parsing with contextual error for optional field
if configPath != "" {
cfg, err := loadConfig(configPath)
cli.NoError(err, "unable to load config from %q", configPath)
}
// Avoid - Must functions panic without context
addr := MustParseAddress(hex)
// Avoid - returns error without user-friendly context
if err != nil {
return err
}- When working with GRT-denominated values, use the project
sds.GRTtype and helpers (ParseGRT,BigInt, etc.) instead of adding local decimal parsing or formatting helpers. - Keep
*big.Intusage at explicit boundaries only: ABI encoding, contract calls, protobuf conversion, or third-party APIs that require it. - Before introducing a new helper for money/addresses/signatures, check whether the repo already has a project-level type or utility for that domain.
- If contract ABIs/artifacts are needed outside development-only code, move them to a shared package instead of importing from
devenv.
- Do not lock another struct’s mutex from outside the owning type.
- Public methods should be the synchronization boundary;
*Lockedhelpers are acceptable only when fully internal to the owning type. - Avoid holding mutexes across blocking network I/O unless that serialization is deliberate and clearly documented.
- For long-lived bidi streams, prefer a dedicated owner/manager over goroutine-per-operation wrappers.
- Treat timeouts/retries for control-plane communication as explicit policy, not hidden constants in handlers.
- For reproducible demo/dev workflows, prefer fail-fast required environment/config over silent hardcoded fallbacks.
- Use defaults only when they are an intentional part of the user-facing UX, not as hidden implementation conveniences.
- Add a short comment for non-obvious transport/network setup (for example, h2c/plaintext HTTP/2 client configuration).
- Do not make insecure transport the default for code paths that may later be used outside local/demo workflows.
- If plaintext or insecure TLS behavior is needed for local development, gate it behind explicit configuration and keep production-oriented defaults secure.
- All builds must pass before committing
- Run
go vetto ensure code quality - Use
go mod tidyafter updating dependencies - Test coverage exists for event.go and utils.go
- Known bug: utils.go line 49 uses
countbefore it's set (results in +Inf for average)