Skip to content

Commit c5805c5

Browse files
committed
feat: Add healthcheck command in nerdctl
Signed-off-by: Subash Kotha <[email protected]>
1 parent 4bde79d commit c5805c5

File tree

21 files changed

+2032
-15
lines changed

21 files changed

+2032
-15
lines changed

cmd/nerdctl/container/container.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ func Command() *cobra.Command {
5454
pruneCommand(),
5555
StatsCommand(),
5656
AttachCommand(),
57+
HealthCheckCommand(),
5758
)
5859
AddCpCommand(cmd)
5960
return cmd

cmd/nerdctl/container/container_create.go

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,40 @@ func createOptions(cmd *cobra.Command) (types.ContainerCreateOptions, error) {
258258
}
259259
// #endregion
260260

261+
// #region for healthcheck flags
262+
opt.HealthCmd, err = cmd.Flags().GetString("health-cmd")
263+
if err != nil {
264+
return opt, err
265+
}
266+
opt.HealthInterval, err = cmd.Flags().GetDuration("health-interval")
267+
if err != nil {
268+
return opt, err
269+
}
270+
opt.HealthTimeout, err = cmd.Flags().GetDuration("health-timeout")
271+
if err != nil {
272+
return opt, err
273+
}
274+
opt.HealthRetries, err = cmd.Flags().GetInt("health-retries")
275+
if err != nil {
276+
return opt, err
277+
}
278+
opt.HealthStartPeriod, err = cmd.Flags().GetDuration("health-start-period")
279+
if err != nil {
280+
return opt, err
281+
}
282+
opt.HealthStartInterval, err = cmd.Flags().GetDuration("health-start-interval")
283+
if err != nil {
284+
return opt, err
285+
}
286+
opt.NoHealthcheck, err = cmd.Flags().GetBool("no-healthcheck")
287+
if err != nil {
288+
return opt, err
289+
}
290+
if err := helpers.ValidateHealthcheckFlags(opt); err != nil {
291+
return opt, err
292+
}
293+
// #endregion
294+
261295
// #region for intel RDT flags
262296
opt.RDTClass, err = cmd.Flags().GetString("rdt-class")
263297
if err != nil {
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
/*
2+
Copyright The containerd Authors.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
limitations under the License.
15+
*/
16+
17+
package container
18+
19+
import (
20+
"context"
21+
"fmt"
22+
23+
"github.com/spf13/cobra"
24+
25+
containerd "github.com/containerd/containerd/v2/client"
26+
27+
"github.com/containerd/nerdctl/v2/cmd/nerdctl/completion"
28+
"github.com/containerd/nerdctl/v2/cmd/nerdctl/helpers"
29+
"github.com/containerd/nerdctl/v2/pkg/clientutil"
30+
"github.com/containerd/nerdctl/v2/pkg/cmd/container"
31+
"github.com/containerd/nerdctl/v2/pkg/idutil/containerwalker"
32+
)
33+
34+
// HealthCheckCommand returns a cobra command for `nerdctl container healthcheck`
35+
func HealthCheckCommand() *cobra.Command {
36+
var healthCheckCommand = &cobra.Command{
37+
Use: "healthcheck [flags] CONTAINER",
38+
Short: "Execute the health check command in a container",
39+
Args: cobra.ExactArgs(1),
40+
RunE: healthCheckAction,
41+
ValidArgsFunction: healthCheckShellComplete,
42+
SilenceUsage: true,
43+
SilenceErrors: true,
44+
}
45+
46+
return healthCheckCommand
47+
}
48+
49+
func healthCheckAction(cmd *cobra.Command, args []string) error {
50+
globalOptions, err := helpers.ProcessRootCmdFlags(cmd)
51+
if err != nil {
52+
return err
53+
}
54+
55+
client, ctx, cancel, err := clientutil.NewClient(cmd.Context(), globalOptions.Namespace, globalOptions.Address)
56+
if err != nil {
57+
return err
58+
}
59+
defer cancel()
60+
61+
containerID := args[0]
62+
walker := &containerwalker.ContainerWalker{
63+
Client: client,
64+
OnFound: func(ctx context.Context, found containerwalker.Found) error {
65+
if found.MatchCount > 1 {
66+
return fmt.Errorf("multiple IDs found with provided prefix: %s", found.Req)
67+
}
68+
return container.HealthCheck(ctx, client, found.Container)
69+
},
70+
}
71+
72+
n, err := walker.Walk(ctx, containerID)
73+
if err != nil {
74+
return err
75+
} else if n == 0 {
76+
return fmt.Errorf("no such container %s", containerID)
77+
}
78+
return nil
79+
}
80+
81+
func healthCheckShellComplete(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
82+
return completion.ContainerNames(cmd, func(status containerd.ProcessStatus) bool {
83+
return status == containerd.Running
84+
})
85+
}

0 commit comments

Comments
 (0)