mirror of
https://github.com/psviderski/uncloud.git
synced 2026-08-26 19:13:34 +00:00
chore: add --yes flag to 'uc machine init/add' to auto-confirm machine reset
This commit is contained in:
@@ -27,6 +27,7 @@ type addOptions struct {
|
|||||||
publicIP string
|
publicIP string
|
||||||
sshKey string
|
sshKey string
|
||||||
version string
|
version string
|
||||||
|
yes bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewAddCommand() *cobra.Command {
|
func NewAddCommand() *cobra.Command {
|
||||||
@@ -41,6 +42,8 @@ Connection methods:
|
|||||||
ssh+cli://user@host - Use system SSH command (supports ProxyJump, SSH config)`,
|
ssh+cli://user@host - Use system SSH command (supports ProxyJump, SSH config)`,
|
||||||
Args: cobra.ExactArgs(1),
|
Args: cobra.ExactArgs(1),
|
||||||
RunE: func(cmd *cobra.Command, args []string) error {
|
RunE: func(cmd *cobra.Command, args []string) error {
|
||||||
|
cli.BindEnvToFlag(cmd, "yes", "UNCLOUD_AUTO_CONFIRM")
|
||||||
|
|
||||||
uncli := cmd.Context().Value("cli").(*cli.CLI)
|
uncli := cmd.Context().Value("cli").(*cli.CLI)
|
||||||
|
|
||||||
// Determine if SSH CLI needs to be used and strip scheme
|
// Determine if SSH CLI needs to be used and strip scheme
|
||||||
@@ -88,6 +91,9 @@ Connection methods:
|
|||||||
&opts.version, "version", "latest",
|
&opts.version, "version", "latest",
|
||||||
"Version of the Uncloud daemon to install on the machine.",
|
"Version of the Uncloud daemon to install on the machine.",
|
||||||
)
|
)
|
||||||
|
cmd.Flags().BoolVarP(&opts.yes, "yes", "y", false,
|
||||||
|
"Auto-confirm prompts (e.g., resetting an already initialised machine).\n"+
|
||||||
|
"Should be explicitly set when running non-interactively, e.g., in CI/CD pipelines. [$UNCLOUD_AUTO_CONFIRM]")
|
||||||
|
|
||||||
return cmd
|
return cmd
|
||||||
}
|
}
|
||||||
@@ -113,6 +119,7 @@ func add(ctx context.Context, uncli *cli.CLI, remoteMachine *cli.RemoteMachine,
|
|||||||
RemoteMachine: remoteMachine,
|
RemoteMachine: remoteMachine,
|
||||||
SkipInstall: opts.noInstall,
|
SkipInstall: opts.noInstall,
|
||||||
Version: opts.version,
|
Version: opts.version,
|
||||||
|
AutoConfirm: opts.yes,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
|||||||
@@ -28,6 +28,7 @@ type initOptions struct {
|
|||||||
sshKey string
|
sshKey string
|
||||||
version string
|
version string
|
||||||
context string
|
context string
|
||||||
|
yes bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewInitCommand() *cobra.Command {
|
func NewInitCommand() *cobra.Command {
|
||||||
@@ -56,6 +57,8 @@ Connection methods:
|
|||||||
// TODO: support initialising a cluster on the local machine.
|
// TODO: support initialising a cluster on the local machine.
|
||||||
Args: cobra.MaximumNArgs(1),
|
Args: cobra.MaximumNArgs(1),
|
||||||
RunE: func(cmd *cobra.Command, args []string) error {
|
RunE: func(cmd *cobra.Command, args []string) error {
|
||||||
|
cli.BindEnvToFlag(cmd, "yes", "UNCLOUD_AUTO_CONFIRM")
|
||||||
|
|
||||||
uncli := cmd.Context().Value("cli").(*cli.CLI)
|
uncli := cmd.Context().Value("cli").(*cli.CLI)
|
||||||
|
|
||||||
var remoteMachine *cli.RemoteMachine
|
var remoteMachine *cli.RemoteMachine
|
||||||
@@ -82,6 +85,11 @@ Connection methods:
|
|||||||
return initCluster(cmd.Context(), uncli, remoteMachine, opts)
|
return initCluster(cmd.Context(), uncli, remoteMachine, opts)
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cmd.Flags().StringVarP(
|
||||||
|
&opts.context, "context", "c", cli.DefaultContextName,
|
||||||
|
"Name of the new context to be created in the Uncloud config to manage the cluster.",
|
||||||
|
)
|
||||||
cmd.Flags().StringVar(&opts.dnsEndpoint, "dns-endpoint", dns.DefaultUncloudDNSAPIEndpoint,
|
cmd.Flags().StringVar(&opts.dnsEndpoint, "dns-endpoint", dns.DefaultUncloudDNSAPIEndpoint,
|
||||||
"API endpoint for the Uncloud DNS service.")
|
"API endpoint for the Uncloud DNS service.")
|
||||||
cmd.Flags().StringVarP(
|
cmd.Flags().StringVarP(
|
||||||
@@ -119,10 +127,9 @@ Connection methods:
|
|||||||
&opts.version, "version", "latest",
|
&opts.version, "version", "latest",
|
||||||
"Version of the Uncloud daemon to install on the machine.",
|
"Version of the Uncloud daemon to install on the machine.",
|
||||||
)
|
)
|
||||||
cmd.Flags().StringVarP(
|
cmd.Flags().BoolVarP(&opts.yes, "yes", "y", false,
|
||||||
&opts.context, "context", "c", cli.DefaultContextName,
|
"Auto-confirm prompts (e.g., resetting an already initialised machine).\n"+
|
||||||
"Name of the new context to be created in the Uncloud config to manage the cluster.",
|
"Should be explicitly set when running non-interactively, e.g., in CI/CD pipelines. [$UNCLOUD_AUTO_CONFIRM]")
|
||||||
)
|
|
||||||
|
|
||||||
return cmd
|
return cmd
|
||||||
}
|
}
|
||||||
@@ -159,6 +166,7 @@ func initCluster(ctx context.Context, uncli *cli.CLI, remoteMachine *cli.RemoteM
|
|||||||
RemoteMachine: remoteMachine,
|
RemoteMachine: remoteMachine,
|
||||||
SkipInstall: opts.noInstall,
|
SkipInstall: opts.noInstall,
|
||||||
Version: opts.version,
|
Version: opts.version,
|
||||||
|
AutoConfirm: opts.yes,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
|||||||
+14
-2
@@ -162,6 +162,7 @@ type InitClusterOptions struct {
|
|||||||
RemoteMachine *RemoteMachine
|
RemoteMachine *RemoteMachine
|
||||||
SkipInstall bool
|
SkipInstall bool
|
||||||
Version string
|
Version string
|
||||||
|
AutoConfirm bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// InitCluster initialises a new cluster on a remote machine and returns a client to interact with the cluster.
|
// InitCluster initialises a new cluster on a remote machine and returns a client to interact with the cluster.
|
||||||
@@ -197,7 +198,12 @@ func (cli *CLI) initRemoteMachine(ctx context.Context, opts InitClusterOptions)
|
|||||||
return nil, fmt.Errorf("inspect machine: %w", err)
|
return nil, fmt.Errorf("inspect machine: %w", err)
|
||||||
}
|
}
|
||||||
if minfo.Id != "" {
|
if minfo.Id != "" {
|
||||||
if err = promptResetMachine(ctx, machineClient.MachineClient); err != nil {
|
if !opts.AutoConfirm {
|
||||||
|
if err = promptResetMachine(); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if err = resetAndWaitMachine(ctx, machineClient.MachineClient); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -297,6 +303,7 @@ type AddMachineOptions struct {
|
|||||||
RemoteMachine *RemoteMachine
|
RemoteMachine *RemoteMachine
|
||||||
SkipInstall bool
|
SkipInstall bool
|
||||||
Version string
|
Version string
|
||||||
|
AutoConfirm bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// AddMachine provisions a remote machine and adds it to the cluster. It returns a cluster client and a machine client.
|
// AddMachine provisions a remote machine and adds it to the cluster. It returns a cluster client and a machine client.
|
||||||
@@ -342,7 +349,12 @@ func (cli *CLI) AddMachine(ctx context.Context, opts AddMachineOptions) (*client
|
|||||||
return nil, nil, fmt.Errorf("machine is already a member of this cluster (%s)", minfo.Name)
|
return nil, nil, fmt.Errorf("machine is already a member of this cluster (%s)", minfo.Name)
|
||||||
}
|
}
|
||||||
|
|
||||||
if err = promptResetMachine(ctx, machineClient.MachineClient); err != nil {
|
if !opts.AutoConfirm {
|
||||||
|
if err = promptResetMachine(); err != nil {
|
||||||
|
return nil, nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if err = resetAndWaitMachine(ctx, machineClient.MachineClient); err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+13
-1
@@ -2,6 +2,7 @@ package cli
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
@@ -86,7 +87,13 @@ func provisionMachine(ctx context.Context, exec sshexec.Executor, version string
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func promptResetMachine(ctx context.Context, machineClient pb.MachineClient) error {
|
func promptResetMachine() error {
|
||||||
|
if !IsStdinTerminal() {
|
||||||
|
return errors.New("the remote machine is already initialised as a cluster member; " +
|
||||||
|
"cannot ask to confirm reset in non-interactive mode, " +
|
||||||
|
"use --yes flag or set UNCLOUD_AUTO_CONFIRM=true to auto-confirm")
|
||||||
|
}
|
||||||
|
|
||||||
var confirm bool
|
var confirm bool
|
||||||
form := huh.NewForm(
|
form := huh.NewForm(
|
||||||
huh.NewGroup(
|
huh.NewGroup(
|
||||||
@@ -110,10 +117,15 @@ func promptResetMachine(ctx context.Context, machineClient pb.MachineClient) err
|
|||||||
return fmt.Errorf("remote machine is already initialised as a cluster member")
|
return fmt.Errorf("remote machine is already initialised as a cluster member")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func resetAndWaitMachine(ctx context.Context, machineClient pb.MachineClient) error {
|
||||||
if _, err := machineClient.Reset(ctx, &pb.ResetRequest{}); err != nil {
|
if _, err := machineClient.Reset(ctx, &pb.ResetRequest{}); err != nil {
|
||||||
return fmt.Errorf("reset remote machine: %w. You can also manually run 'uncloud-uninstall' "+
|
return fmt.Errorf("reset remote machine: %w. You can also manually run 'uncloud-uninstall' "+
|
||||||
"on the remote machine to fully uninstall Uncloud from it", err)
|
"on the remote machine to fully uninstall Uncloud from it", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Println("Resetting the remote machine...")
|
fmt.Println("Resetting the remote machine...")
|
||||||
if err := waitMachineReady(ctx, machineClient, 1*time.Minute); err != nil {
|
if err := waitMachineReady(ctx, machineClient, 1*time.Minute); err != nil {
|
||||||
return fmt.Errorf("wait for machine to be ready after reset: %w", err)
|
return fmt.Errorf("wait for machine to be ready after reset: %w", err)
|
||||||
|
|||||||
Reference in New Issue
Block a user