diff --git a/.github/workflows/pr-build.yml b/.github/workflows/pr-build.yml index 51d660c..e333d47 100644 --- a/.github/workflows/pr-build.yml +++ b/.github/workflows/pr-build.yml @@ -40,7 +40,7 @@ jobs: fi - name: Build - run: bazel build //:client + run: bazel build //... # Template for future matrix builds # matrix-build: diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml new file mode 100644 index 0000000..c6f1f89 --- /dev/null +++ b/.pre-commit-config.yaml @@ -0,0 +1,9 @@ +repos: + - repo: local + hooks: + - id: gofmt-bazel + name: Format Go code via Bazel (rules_go) + entry: bazel run @io_bazel_rules_go//go -- fmt ./... + language: system + pass_filenames: false + types: [go] diff --git a/BUILD b/BUILD index f5da7f3..3027457 100644 --- a/BUILD +++ b/BUILD @@ -22,12 +22,3 @@ go_binary( embed = [":go_default_library"], visibility = ["//visibility:public"], ) - -go_binary( - name = "test", - srcs = ["test.go"], - deps = [ - "@com_github_golang_protobuf//proto:go_default_library", - "@remoteapis//build/bazel/remote/execution/v2:go_default_library", - ], -) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..18faa08 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,53 @@ +## Contributing + +Thank you for helping improve `bf-client`! This guide outlines the basics for making high‑quality contributions that are easy to review and maintain. + +### Prerequisites +- Go 1.23 (see `go.mod`) +- Bazel (build/test) +- Git + +### Getting started +1. Fork the repo and create a feature branch from the default branch. +2. Make small, focused commits with clear messages. +3. Open a pull request early for feedback; keep PRs scoped and reviewable. + +### Build and test +- Bazel (preferred): + - Build: `bazel build //...` + - Test: `bazel test //...` +- Native Go (if helpful locally): + - `go build ./...` + - `go test ./...` + +All PRs should pass tests and build cleanly. + +### Formatting and static checks +- Always run formatting before committing: + - `go fmt ./...` + - Optionally also: `gofmt -s -w .` +- Prefer to run basic static checks locally: + - `go vet ./...` + +CI may reject PRs that aren’t formatted. If you’re unsure, re‑run `go fmt ./...`. + + +### Pre-commit (optional but encouraged) +Use `pre-commit` to auto‑format and vet changes locally. + +Then run: +```bash +pre-commit install +``` + +### Commit and PR checklist +- [ ] Code compiles and tests pass (`bazel test //...`) +- [ ] Public APIs and non‑obvious logic documented +- [ ] PR description explains the why and the what + +### Communication +- Prefer small, iterative PRs; include context and tradeoffs. +- Be kind and constructive in reviews; propose changes with rationale. + +Thanks for contributing! + diff --git a/MODULE.bazel.lock b/MODULE.bazel.lock index 2dbff73..1c87cff 100644 --- a/MODULE.bazel.lock +++ b/MODULE.bazel.lock @@ -242,7 +242,7 @@ "moduleExtensions": { "//:extensions.bzl%build_deps": { "general": { - "bzlTransitiveDigest": "yzPfL9UwdpPYFRKWTv5Ol84AkkFQRm/y91nJeUagJz4=", + "bzlTransitiveDigest": "4McQAVUuB28g6/K1krYOhheuC9nBITj+74GIhJvArC0=", "usagesDigest": "N1be+WNYxoeG1JN4CaIE1KMt+fq1c0PjhQ9M3tOJvU0=", "recordedFileInputs": {}, "recordedDirentsInputs": {}, @@ -252,19 +252,12 @@ "repoRuleId": "@@bazel_tools//tools/build_defs/repo:http.bzl%http_archive", "attributes": { "build_file": "@@//:BUILD.buildfarm", - "sha256": "cf47ea9674bde436cfafdcfc772be0fb5998482185c0e339ee4170370f025cf8", - "strip_prefix": "buildfarm-6be2f5e33ca9e3a0c7a2be253d52a53c3df4eddc/src/main/protobuf/build/buildfarm/v1test/", + "sha256": "575c657a565c4e986ba10b55c6e652c6ec7a68c2222b4951a9362dc0e53e3d2d", + "strip_prefix": "buildfarm-2.16.0/src/main/protobuf/build/buildfarm/v1test/", "urls": [ - "https://github.com/buildfarm/buildfarm/archive/6be2f5e33ca9e3a0c7a2be253d52a53c3df4eddc.zip" + "https://github.com/buildfarm/buildfarm/archive/refs/tags/2.16.0.zip" ] } - }, - "local_buildfarm": { - "repoRuleId": "@@bazel_tools//tools/build_defs/repo:local.bzl%new_local_repository", - "attributes": { - "build_file": "@@//:BUILD.buildfarm", - "path": "../buildfarm/src/main/protobuf/build/buildfarm/v1test" - } } }, "recordedRepoMappingEntries": [ diff --git a/client/operation.go b/client/operation.go index 29ef8be..15ef41c 100644 --- a/client/operation.go +++ b/client/operation.go @@ -30,7 +30,10 @@ func ExecuteOperationMetadata(op *longrunning.Operation) (*reapi.ExecuteOperatio } return qm.ExecuteOperationMetadata, nil } - return nil, errors.New("Unexpected metadata: " + proto.MarshalTextString(op)) + // Gracefully handle unexpected or unknown metadata types by returning an + // empty ExecuteOperationMetadata instead of an error to avoid crashing + // callers that expect a non-nil metadata instance. + return &reapi.ExecuteOperationMetadata{}, nil } func RequestMetadata(o *longrunning.Operation) *reapi.RequestMetadata { diff --git a/extensions.bzl b/extensions.bzl index 7577ead..bdc928a 100644 --- a/extensions.bzl +++ b/extensions.bzl @@ -4,10 +4,10 @@ def _buildfarm_extension_impl(_ctx): http_archive( name = "buildfarm", build_file = "@//:BUILD.buildfarm", - sha256 = "cf47ea9674bde436cfafdcfc772be0fb5998482185c0e339ee4170370f025cf8", - strip_prefix = "buildfarm-6be2f5e33ca9e3a0c7a2be253d52a53c3df4eddc/src/main/protobuf/build/buildfarm/v1test/", + sha256 = "575c657a565c4e986ba10b55c6e652c6ec7a68c2222b4951a9362dc0e53e3d2d", + strip_prefix = "buildfarm-2.16.0/src/main/protobuf/build/buildfarm/v1test/", urls = [ - "https://github.com/buildfarm/buildfarm/archive/6be2f5e33ca9e3a0c7a2be253d52a53c3df4eddc.zip", + "https://github.com/buildfarm/buildfarm/archive/refs/tags/2.16.0.zip", ], ) diff --git a/view/operation_list.go b/view/operation_list.go index 3d544e2..af863d1 100644 --- a/view/operation_list.go +++ b/view/operation_list.go @@ -61,7 +61,7 @@ func NewOperationList(a *client.App, mode int, v View) *operationList { start := time.Now() a.Fetches++ status, err := c.Status(context.Background(), &bfpb.BackplaneStatusRequest{ - InstanceName: "shard", + InstanceName: a.Instance, }) a.LastReapiLatency = time.Since(start) if err != nil { @@ -370,6 +370,8 @@ func (v *operationList) Update() { if v.opcache.Contains(op.Name) { continue } + // avoid concurrent v.a.Ops map read/write + v.a.Mutex.Lock() if o, ok := v.a.Ops[op.Name]; !ok || o == nil { m := op.Metadata if m == nil { @@ -378,6 +380,7 @@ func (v *operationList) Update() { go getExecution(v.a, op.Name, v.a.Conn, &wg) } } + v.a.Mutex.Unlock() } wg.Wait() v.opNames = make([]string, 0) diff --git a/view/queue.go b/view/queue.go index b6231d2..8877368 100644 --- a/view/queue.go +++ b/view/queue.go @@ -271,7 +271,7 @@ func (v *Queue) Update() { } start := time.Now() st, err := c.Status(context.Background(), &bfpb.BackplaneStatusRequest{ - InstanceName: "shard", + InstanceName: v.a.Instance, }) v.a.LastReapiLatency = time.Since(start) if err == nil { diff --git a/view/worker.go b/view/worker.go index 689b118..c05ce29 100644 --- a/view/worker.go +++ b/view/worker.go @@ -554,12 +554,18 @@ func pausedStyle(p bool) ui.Style { func (v *worker) Update() { conn := v.a.GetWorkerConn(v.w, v.a.CA) workerProfile := bfpb.NewWorkerProfileClient(conn) - profile, err := workerProfile.GetWorkerProfile(context.Background(), &bfpb.WorkerProfileRequest{}) + profile, err := workerProfile.GetWorkerProfile(context.Background(), &bfpb.WorkerProfileRequest{ + InstanceName: v.a.Instance, + WorkerName: v.w, + }) if err == nil { v.profile = profile } c := bfpb.NewWorkerControlClient(conn) - r, err := c.PipelineChange(context.Background(), &bfpb.WorkerPipelineChangeRequest{}) + r, err := c.PipelineChange(context.Background(), &bfpb.WorkerPipelineChangeRequest{ + InstanceName: v.a.Instance, + WorkerName: v.w, + }) if err != nil { panic(err) }