-
Notifications
You must be signed in to change notification settings - Fork 591
Implement the readiness endpoint for health checking #2015
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
ee89782
65ed547
fd5512c
703c624
4a3c745
358825e
a79c88c
1fb4a0d
7759eb5
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -2,16 +2,17 @@ package agent | |
|
|
||
| import ( | ||
| "context" | ||
| "errors" | ||
| "fmt" | ||
| "net/http" | ||
| _ "net/http/pprof" //nolint: gosec // import registers routes on DefaultServeMux | ||
| "os" | ||
| "path" | ||
| "runtime" | ||
| "sync" | ||
| "time" | ||
|
|
||
| "github.com/spiffe/go-spiffe/v2/spiffeid" | ||
| api_workload "github.com/spiffe/spire/api/workload" | ||
| admin_api "github.com/spiffe/spire/pkg/agent/api" | ||
| node_attestor "github.com/spiffe/spire/pkg/agent/attestor/node" | ||
| workload_attestor "github.com/spiffe/spire/pkg/agent/attestor/workload" | ||
|
|
@@ -30,6 +31,8 @@ import ( | |
| "github.com/spiffe/spire/proto/spire/api/server/bundle/v1" | ||
| _ "golang.org/x/net/trace" // registers handlers on the DefaultServeMux | ||
| "google.golang.org/grpc" | ||
| "google.golang.org/grpc/codes" | ||
| "google.golang.org/grpc/status" | ||
| ) | ||
|
|
||
| type Agent struct { | ||
|
|
@@ -97,7 +100,7 @@ func (a *Agent) Run(ctx context.Context) error { | |
|
|
||
| endpoints := a.newEndpoints(cat, metrics, manager) | ||
|
|
||
| if err := healthChecks.AddCheck("agent", a, time.Minute); err != nil { | ||
| if err := healthChecks.AddCheck("agent", a); err != nil { | ||
| return fmt.Errorf("failed adding healthcheck: %v", err) | ||
| } | ||
|
|
||
|
|
@@ -261,5 +264,23 @@ func (a *Agent) agentSVIDPath() string { | |
|
|
||
| // Status is used as a top-level health check for the Agent. | ||
| func (a *Agent) Status() (interface{}, error) { | ||
| return nil, nil | ||
| client := api_workload.NewX509Client(&api_workload.X509ClientConfig{ | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The same situation as the server applies here also. |
||
| Addr: a.c.BindAddress, | ||
| FailOnError: true, | ||
| }) | ||
| defer client.Stop() | ||
|
|
||
| errCh := make(chan error, 1) | ||
| go func() { | ||
| errCh <- client.Start() | ||
| }() | ||
|
|
||
| err := <-errCh | ||
| if status.Code(err) == codes.Unavailable { | ||
| return nil, errors.New("workload api is unavailable") //nolint: golint // error is (ab)used for CLI output | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think that it would be good to expose the error captured in |
||
| } | ||
|
|
||
| return health.Details{ | ||
| Message: "successfully created a workload api client to fetch x509 svid", | ||
| }, nil | ||
|
Comment on lines
+267
to
+285
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I had something very similar in mind. I think it needs a Obviously, we would want to add a test for the race detector on that select as well. |
||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -18,6 +18,21 @@ type Config struct { | |
| UnusedKeys []string `hcl:",unusedKeys"` | ||
| } | ||
|
|
||
| // getAddress returns an address suitable for use as http.Server.Addr. | ||
| func (c *Config) getAddress() string { | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Moving this method above |
||
| host := "localhost" | ||
| if c.BindAddress != "" { | ||
| host = c.BindAddress | ||
| } | ||
|
|
||
| port := "80" | ||
| if c.BindPort != "" { | ||
| port = c.BindPort | ||
| } | ||
|
|
||
| return fmt.Sprintf("%s:%s", host, port) | ||
| } | ||
|
|
||
| // getReadyPath returns the configured value or a default | ||
| func (c *Config) getReadyPath() string { | ||
| if c.ReadyPath == "" { | ||
|
|
@@ -36,17 +51,7 @@ func (c *Config) getLivePath() string { | |
| return c.LivePath | ||
| } | ||
|
|
||
| // getAddress returns an address suitable for use as http.Server.Addr. | ||
| func (c *Config) getAddress() string { | ||
| host := "localhost" | ||
| if c.BindAddress != "" { | ||
| host = c.BindAddress | ||
| } | ||
|
|
||
| port := "80" | ||
| if c.BindPort != "" { | ||
| port = c.BindPort | ||
| } | ||
|
|
||
| return fmt.Sprintf("%s:%s", host, port) | ||
| // Details are additional data to be used when the system is ready | ||
| type Details struct { | ||
| Message string `json:"message,omitempty"` | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -2,16 +2,17 @@ package server | |
|
|
||
| import ( | ||
| "context" | ||
| "errors" | ||
| "fmt" | ||
| "net/http" | ||
| _ "net/http/pprof" //nolint: gosec // import registers routes on DefaultServeMux | ||
| "net/url" | ||
| "os" | ||
| "runtime" | ||
| "sync" | ||
| "time" | ||
|
|
||
| "github.com/andres-erbsen/clock" | ||
| server_util "github.com/spiffe/spire/cmd/spire-server/util" | ||
| "github.com/spiffe/spire/pkg/common/health" | ||
| "github.com/spiffe/spire/pkg/common/hostservices/metricsservice" | ||
| common_services "github.com/spiffe/spire/pkg/common/plugin/hostservices" | ||
|
|
@@ -29,6 +30,7 @@ import ( | |
| "github.com/spiffe/spire/pkg/server/plugin/hostservices" | ||
| "github.com/spiffe/spire/pkg/server/registration" | ||
| "github.com/spiffe/spire/pkg/server/svid" | ||
| "github.com/spiffe/spire/proto/spire/api/server/bundle/v1" | ||
| "google.golang.org/grpc" | ||
| ) | ||
|
|
||
|
|
@@ -158,7 +160,7 @@ func (s *Server) run(ctx context.Context) (err error) { | |
|
|
||
| registrationManager := s.newRegistrationManager(cat, metrics) | ||
|
|
||
| if err := healthChecks.AddCheck("server", s, time.Minute); err != nil { | ||
| if err := healthChecks.AddCheck("server", s); err != nil { | ||
| return fmt.Errorf("failed adding healthcheck: %v", err) | ||
| } | ||
|
|
||
|
|
@@ -384,5 +386,23 @@ func (s *Server) validateTrustDomain(ctx context.Context, ds datastore.DataStore | |
|
|
||
| // Status is used as a top-level health check for the Server. | ||
| func (s *Server) Status() (interface{}, error) { | ||
| return nil, nil | ||
| client, err := server_util.NewServerClient(s.config.BindUDSAddress.Name) | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'm realizing that there could be a race here at startup time, where this can be executed before the server is serving. In that case, throwing this error could be confusing. |
||
| if err != nil { | ||
| return nil, errors.New("cannot create registration client") | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think that it would be good to expose the error captured in |
||
| } | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We need to defer a call to
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I fixed it with 4a3c745. |
||
| defer client.Release() | ||
|
|
||
| bundleClient := client.NewBundleClient() | ||
|
|
||
| // Currently using the ability to fetch a bundle as the health check. This | ||
| // **could** be problematic if the Upstream CA signing process is lengthy. | ||
| // As currently coded however, the API isn't served until after | ||
| // the server CA has been signed by upstream. | ||
| if _, err := bundleClient.GetBundle(context.Background(), &bundle.GetBundleRequest{}); err != nil { | ||
| return nil, errors.New("unable to fetch bundle") | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think that it would be good to expose the error captured in |
||
| } | ||
|
|
||
| return health.Details{ | ||
| Message: "successfully fetched bundle", | ||
| }, nil | ||
| } | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: All the minor whitespace corrections in the doc comments distract from the main purpose of the pull request. I agree the corrections should be made, it would be easier to review in a separate commit.