[PR #6818] [client] Make netbird up wait for the daemon to become ready #27190

Open
opened 2026-08-05 07:08:20 -04:00 by saavagebueno · 0 comments
Owner

📋 Pull Request Information

Original PR: https://github.com/netbirdio/netbird/pull/6818
Author: @pappz
Created: 7/17/2026
Status: 🔄 Open

Base: mainHead: fix/cli-up-wait-for-daemon


📝 Commits (1)

  • ccb271b [client] Make netbird up wait for the daemon to become ready

📊 Changes

11 files changed (+373 additions, -82 deletions)

View changed files

📝 client/Dockerfile (+1 -2)
📝 client/Dockerfile-rootless (+1 -2)
client/cmd/dial_test.go (+176 -0)
📝 client/cmd/root.go (+61 -6)
📝 client/cmd/service_controller.go (+4 -0)
📝 client/cmd/up.go (+74 -3)
📝 client/netbird-entrypoint.sh (+18 -62)
📝 client/proto/daemon.pb.go (+17 -4)
📝 client/proto/daemon.proto (+5 -0)
📝 client/server/server.go (+15 -1)
📝 e2e/harness/Dockerfile.client (+1 -2)

📄 Description

The CLI up path only tolerated a not-yet-ready daemon via a 10s blocking dial, so "netbird service start" immediately followed by "netbird up" (e.g. a container entrypoint) failed with a generic "daemon not running" error. The container entrypoint worked around this with a shell poll loop (status --check live) before running up.

Move the readiness wait into the CLI, mirroring how the GUI already dials:

  • DialClientGRPCServer now uses grpc.NewClient with a tuned reconnect backoff and waits for the connection to reach READY (retrying on TRANSIENT_FAILURE) up to a 30s deadline, instead of grpc.DialContext + WithBlock with a hard 10s timeout.
  • up now polls Status via waitForDaemonStatus, retrying while the RPC is Unavailable (socket up but service not yet registered).

Add an explicit daemon-ready signal so clients can wait deterministically instead of heuristically:

  • New optional StatusResponse.daemonReady field (field 5, wire-compatible with older GUIs/daemons which leave it unset). Regenerated with the pinned protoc v33.1 toolchain so no version churn leaks into the diff.
  • The server sets ready once Start succeeds and the DaemonService is registered (SetReady, called from the service controller).
  • waitForDaemonStatus waits for daemonReady=true (or an already-Connected status), with a bounded grace window so older daemons that never set the field are not blocked.

Simplify the container entrypoint accordingly: drop the readiness poll loop (up now waits) and the now-dead NB_ENTRYPOINT_SERVICE_TIMEOUT env, keeping only the daemon+up process glue and SIGTERM forwarding for clean shutdown.

Describe your changes

Stack

Checklist

  • Is it a bug fix
  • Is a typo/documentation fix
  • Is a feature enhancement
  • It is a refactor
  • Created tests that fail without the change (if possible)
  • This change does not modify the public API, gRPC protocols, functionality behavior, CLI / service flags, or introduce a new feature — OR I have discussed it with the NetBird team beforehand (link the issue / Slack thread in the description). See CONTRIBUTING.md.

By submitting this pull request, you confirm that you have read and agree to the terms of the Contributor License Agreement.

Documentation

Select exactly one:

  • I added/updated documentation for this change
  • Documentation is not needed for this change (explain why)

Docs PR URL (required if "docs added" is checked)

Paste the PR link from https://github.com/netbirdio/docs here:

https://github.com/netbirdio/docs/pull/__


View with Codesmith Autofix with Codesmith
Need help on this PR? Tag /codesmith with what you need. Autofix is disabled.

Summary by CodeRabbit

  • Reliability Improvements

    • Improved client startup handling when the daemon is still initializing or temporarily unavailable.
    • Added clearer readiness detection so clients wait for the daemon to become fully operational.
    • Added bounded connection retries and timeouts to prevent indefinite startup waits.
    • Improved compatibility with older daemon versions.
  • Configuration

    • Removed the obsolete daemon startup timeout setting from client container images.
  • Tests

    • Added coverage for delayed startup, readiness polling, older daemons, and connection timeouts.

🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.

## 📋 Pull Request Information **Original PR:** https://github.com/netbirdio/netbird/pull/6818 **Author:** [@pappz](https://github.com/pappz) **Created:** 7/17/2026 **Status:** 🔄 Open **Base:** `main` ← **Head:** `fix/cli-up-wait-for-daemon` --- ### 📝 Commits (1) - [`ccb271b`](https://github.com/netbirdio/netbird/commit/ccb271b5bb211708bc21361d546e8b6283121741) [client] Make netbird up wait for the daemon to become ready ### 📊 Changes **11 files changed** (+373 additions, -82 deletions) <details> <summary>View changed files</summary> 📝 `client/Dockerfile` (+1 -2) 📝 `client/Dockerfile-rootless` (+1 -2) ➕ `client/cmd/dial_test.go` (+176 -0) 📝 `client/cmd/root.go` (+61 -6) 📝 `client/cmd/service_controller.go` (+4 -0) 📝 `client/cmd/up.go` (+74 -3) 📝 `client/netbird-entrypoint.sh` (+18 -62) 📝 `client/proto/daemon.pb.go` (+17 -4) 📝 `client/proto/daemon.proto` (+5 -0) 📝 `client/server/server.go` (+15 -1) 📝 `e2e/harness/Dockerfile.client` (+1 -2) </details> ### 📄 Description The CLI up path only tolerated a not-yet-ready daemon via a 10s blocking dial, so "netbird service start" immediately followed by "netbird up" (e.g. a container entrypoint) failed with a generic "daemon not running" error. The container entrypoint worked around this with a shell poll loop (status --check live) before running up. Move the readiness wait into the CLI, mirroring how the GUI already dials: - DialClientGRPCServer now uses grpc.NewClient with a tuned reconnect backoff and waits for the connection to reach READY (retrying on TRANSIENT_FAILURE) up to a 30s deadline, instead of grpc.DialContext + WithBlock with a hard 10s timeout. - up now polls Status via waitForDaemonStatus, retrying while the RPC is Unavailable (socket up but service not yet registered). Add an explicit daemon-ready signal so clients can wait deterministically instead of heuristically: - New optional StatusResponse.daemonReady field (field 5, wire-compatible with older GUIs/daemons which leave it unset). Regenerated with the pinned protoc v33.1 toolchain so no version churn leaks into the diff. - The server sets ready once Start succeeds and the DaemonService is registered (SetReady, called from the service controller). - waitForDaemonStatus waits for daemonReady=true (or an already-Connected status), with a bounded grace window so older daemons that never set the field are not blocked. Simplify the container entrypoint accordingly: drop the readiness poll loop (up now waits) and the now-dead NB_ENTRYPOINT_SERVICE_TIMEOUT env, keeping only the daemon+up process glue and SIGTERM forwarding for clean shutdown. ## Describe your changes ## Issue ticket number and link ## Stack <!-- branch-stack --> ### Checklist - [ ] Is it a bug fix - [ ] Is a typo/documentation fix - [ ] Is a feature enhancement - [ ] It is a refactor - [ ] Created tests that fail without the change (if possible) - [ ] This change does **not** modify the public API, gRPC protocols, functionality behavior, CLI / service flags, or introduce a new feature — **OR** I have discussed it with the NetBird team beforehand (link the issue / Slack thread in the description). See [CONTRIBUTING.md](https://github.com/netbirdio/netbird/blob/main/CONTRIBUTING.md#discuss-changes-with-the-netbird-team-first). > By submitting this pull request, you confirm that you have read and agree to the terms of the [Contributor License Agreement](https://github.com/netbirdio/netbird/blob/main/CONTRIBUTOR_LICENSE_AGREEMENT.md). ## Documentation Select exactly one: - [ ] I added/updated documentation for this change - [ ] Documentation is **not needed** for this change (explain why) ### Docs PR URL (required if "docs added" is checked) Paste the PR link from https://github.com/netbirdio/docs here: https://github.com/netbirdio/docs/pull/__ <!-- codesmith:footer --> --- <a href="https://app.blacksmith.sh/netbirdio/codesmith/netbird/pr/6818"><picture><source media="(prefers-color-scheme: dark)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-dark-v2.svg"><source media="(prefers-color-scheme: light)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-light-v2.svg"><img alt="View with Codesmith" src="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-dark-v2.svg"></picture></a> <a href="https://backend.blacksmith.sh/track/enable-autofix?expires=1786887096&installation_id=146802194&pr_number=6818&repository=netbirdio%2Fnetbird&return_to=https%3A%2F%2Fgithub.com%2Fnetbirdio%2Fnetbird%2Fpull%2F6818&signature=38690cfd551fc9630622d20d637abebb1a481b77f2bef145ec0971b136830dd8"><picture><source media="(prefers-color-scheme: dark)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-dark.svg"><source media="(prefers-color-scheme: light)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-light.svg"><img alt="Autofix with Codesmith" src="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-dark.svg"></picture></a> <sup>Need help on this PR? Tag <code>/codesmith</code> with what you need. Autofix is disabled.</sup> <!-- codesmith:autofix:disabled --> <!-- /codesmith:footer --> <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **Reliability Improvements** * Improved client startup handling when the daemon is still initializing or temporarily unavailable. * Added clearer readiness detection so clients wait for the daemon to become fully operational. * Added bounded connection retries and timeouts to prevent indefinite startup waits. * Improved compatibility with older daemon versions. * **Configuration** * Removed the obsolete daemon startup timeout setting from client container images. * **Tests** * Added coverage for delayed startup, readiness polling, older daemons, and connection timeouts. <!-- end of auto-generated comment: release notes by coderabbit.ai --> --- <sub>🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.</sub>
saavagebueno added the pull-request label 2026-08-05 07:08:20 -04:00
Sign in to join this conversation.
No Label pull-request
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: DYNR/netbird#27190