Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions app/app.go
Original file line number Diff line number Diff line change
Expand Up @@ -252,7 +252,7 @@ func (c colimaApp) SSH(args ...string) error {
// peek the current directory to see if it is mounted to prevent `cd` errors
// with limactl ssh
if err := func() error {
conf, err := limautil.InstanceConfig()
conf, err := configmanager.LoadInstance()
if err != nil {
return err
}
Expand Down Expand Up @@ -303,7 +303,7 @@ func (c colimaApp) Status(extended bool) error {
}

driver := "QEMU"
conf, _ := limautil.InstanceConfig()
conf, _ := configmanager.LoadInstance()
if !conf.Empty() {
driver = conf.DriverLabel()
}
Expand Down
41 changes: 27 additions & 14 deletions cmd/start.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import (
"github.com/abiosoft/colima/environment/container/docker"
"github.com/abiosoft/colima/environment/container/kubernetes"
"github.com/abiosoft/colima/util"
"github.com/abiosoft/colima/util/osutil"
log "github.com/sirupsen/logrus"
"github.com/spf13/cobra"
)
Expand Down Expand Up @@ -58,16 +59,11 @@ Run 'colima template' to set the default configurations or 'colima start --edit'
}

// edit flag is specified
err := editConfigFile()
conf, err := editConfigFile()
if err != nil {
return err
}

conf, err = configmanager.Load()
if err != nil {
return fmt.Errorf("error opening config file: %w", err)
}

// validate config
if err := configmanager.ValidateConfig(conf); err != nil {
return fmt.Errorf("error in config file: %w", err)
Expand Down Expand Up @@ -100,9 +96,11 @@ Run 'colima template' to set the default configurations or 'colima start --edit'
return fmt.Errorf("error in config: %w", err)
}

// persist in preparing of application start
if err := configmanager.Save(startCmdArgs.Config); err != nil {
return fmt.Errorf("error preparing config file: %w", err)
// persist in preparation for application start
if startCmdArgs.Flags.SaveConfig {
if err := configmanager.Save(startCmdArgs.Config); err != nil {
return fmt.Errorf("error preparing config file: %w", err)
}
}

return nil
Expand All @@ -121,6 +119,7 @@ const (
)

var defaultK3sArgs = []string{"--disable=traefik"}
var envSaveConfig = osutil.EnvVar("COLIMA_SAVE_CONFIG")

var startCmdArgs struct {
config.Config
Expand All @@ -134,6 +133,7 @@ var startCmdArgs struct {
ActivateRuntime bool
DNSHosts []string
Foreground bool
SaveConfig bool
}
}

Expand All @@ -144,6 +144,11 @@ func init() {
mounts := strings.Join([]string{defaultMountTypeQEMU, "9p", "virtiofs"}, ", ")
types := strings.Join([]string{defaultVMType, "vz"}, ", ")

saveConfigDefault := true
if envSaveConfig.Exists() {
saveConfigDefault = envSaveConfig.Bool()
}

root.Cmd().AddCommand(startCmd)
startCmd.Flags().StringVarP(&startCmdArgs.Runtime, "runtime", "r", docker.Name, "container runtime ("+runtimes+")")
startCmd.Flags().BoolVar(&startCmdArgs.Flags.ActivateRuntime, "activate", true, "set as active Docker/Kubernetes context on startup")
Expand Down Expand Up @@ -180,6 +185,7 @@ func init() {
// config
startCmd.Flags().BoolVarP(&startCmdArgs.Flags.Edit, "edit", "e", false, "edit the configuration file before starting")
startCmd.Flags().StringVar(&startCmdArgs.Flags.Editor, "editor", "", `editor to use for edit e.g. vim, nano, code (default "$EDITOR" env var)`)
startCmd.Flags().BoolVar(&startCmdArgs.Flags.SaveConfig, "save-config", saveConfigDefault, "persist and overwrite config file with (newly) specified flags")

// mounts
startCmd.Flags().StringSliceVarP(&startCmdArgs.Flags.Mounts, "mount", "V", nil, "directories to mount, suffix ':w' for writable")
Expand Down Expand Up @@ -468,11 +474,13 @@ func prepareConfig(cmd *cobra.Command) {
}

// editConfigFile launches an editor to edit the config file.
func editConfigFile() error {
func editConfigFile() (config.Config, error) {
var c config.Config

// preserve the current file in case the user terminates
currentFile, err := os.ReadFile(config.CurrentProfile().File())
if err != nil {
return fmt.Errorf("error reading config file: %w", err)
return c, fmt.Errorf("error reading config file: %w", err)
}

// prepend the config file with termination instruction
Expand All @@ -483,18 +491,23 @@ func editConfigFile() error {

tmpFile, err := waitForUserEdit(startCmdArgs.Flags.Editor, []byte(abort+"\n"+string(currentFile)))
if err != nil {
return fmt.Errorf("error editing config file: %w", err)
return c, fmt.Errorf("error editing config file: %w", err)
}

// if file is empty, abort
if tmpFile == "" {
return fmt.Errorf("empty file, startup aborted")
return c, fmt.Errorf("empty file, startup aborted")
}

defer func() {
_ = os.Remove(tmpFile)
}()
return configmanager.SaveFromFile(tmpFile)
if startCmdArgs.Flags.SaveConfig {
if err := configmanager.SaveFromFile(tmpFile); err != nil {
return c, err
}
}
return configmanager.LoadFrom(tmpFile)
}

func start(app app.App, conf config.Config) error {
Expand Down
21 changes: 13 additions & 8 deletions config/configmanager/configmanager.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,11 @@ func Save(c config.Config) error {

// SaveFromFile loads configuration from file and save as config.
func SaveFromFile(file string) error {
cf, err := LoadFrom(file)
c, err := LoadFrom(file)
if err != nil {
return err
}
return Save(cf)
return Save(c)
}

// SaveToFile saves configuration to file.
Expand Down Expand Up @@ -79,24 +79,29 @@ func ValidateConfig(c config.Config) error {
// Error is only returned if the config file exists but could not be loaded.
// No error is returned if the config file does not exist.
func Load() (config.Config, error) {
cFile := config.CurrentProfile().File()
if _, err := os.Stat(cFile); err != nil {
oldCFile := oldConfigFile()
f := config.CurrentProfile().File()
if _, err := os.Stat(f); err != nil {
oldF := oldConfigFile()

// config file does not exist, check older version for backward compatibility
if _, err := os.Stat(oldCFile); err != nil {
if _, err := os.Stat(oldF); err != nil {
return config.Config{}, nil
}

// older version exists
logrus.Infof("settings from older %s version detected and copied", config.AppName)
if err := cli.Command("cp", oldCFile, cFile).Run(); err != nil {
if err := cli.Command("cp", oldF, f).Run(); err != nil {
logrus.Warn(fmt.Errorf("error copying config: %w, proceeding with defaults", err))
return config.Config{}, nil
}
}

return LoadFrom(cFile)
return LoadFrom(f)
}

// LoadInstance is like Load but returns the config of the currently running instance.
func LoadInstance() (config.Config, error) {
return LoadFrom(config.CurrentProfile().StateFile())
}

// Teardown deletes the config.
Expand Down
6 changes: 3 additions & 3 deletions environment/vm/lima/lima.go
Original file line number Diff line number Diff line change
Expand Up @@ -182,7 +182,7 @@ func (l limaVM) Stop(ctx context.Context, force bool) error {
a.Stage("stopping")

if util.MacOS() {
conf, _ := limautil.InstanceConfig()
conf, _ := configmanager.LoadInstance()
a.Retry("", time.Second*1, 10, func(retryCount int) error {
err := l.daemon.Stop(ctx, conf)
if err != nil {
Expand All @@ -208,7 +208,7 @@ func (l limaVM) Teardown(ctx context.Context) error {
a := l.Init(ctx)

if util.MacOS() {
conf, _ := limautil.InstanceConfig()
conf, _ := configmanager.LoadInstance()
a.Retry("", time.Second*1, 10, func(retryCount int) error {
return l.daemon.Stop(ctx, conf)
})
Expand Down Expand Up @@ -300,7 +300,7 @@ func (l *limaVM) setDiskImage() error {

func (l *limaVM) syncDiskSize(ctx context.Context, conf config.Config) config.Config {
log := l.Logger(ctx)
instance, err := limautil.InstanceConfig()
instance, err := configmanager.LoadInstance()
if err != nil {
// instance config missing, ignore
return conf
Expand Down
9 changes: 0 additions & 9 deletions environment/vm/lima/limautil/instance.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,6 @@ func Instance() (InstanceInfo, error) {
return getInstance(config.CurrentProfile().ID)
}

// InstanceConfig returns the current instance config.
func InstanceConfig() (config.Config, error) {
i, err := Instance()
if err != nil {
return config.Config{}, err
}
return i.Config()
}

// InstanceInfo is the information about a Lima instance
type InstanceInfo struct {
Name string `json:"name,omitempty"`
Expand Down
3 changes: 2 additions & 1 deletion environment/vm/lima/network.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import (
"path/filepath"

"github.com/abiosoft/colima/config"
"github.com/abiosoft/colima/config/configmanager"
"github.com/abiosoft/colima/embedded"
"github.com/abiosoft/colima/environment/vm/lima/limautil"
"github.com/abiosoft/colima/util"
Expand Down Expand Up @@ -39,7 +40,7 @@ func (l *limaVM) replicateHostAddresses(conf config.Config) error {
}

func (l *limaVM) removeHostAddresses() {
conf, _ := limautil.InstanceConfig()
conf, _ := configmanager.LoadInstance()
if !conf.Network.Address && conf.Network.HostAddresses {
for _, ip := range util.HostIPAddresses() {
_ = l.RunQuiet("sudo", "ip", "address", "del", ip.String()+"/24", "dev", "lo")
Expand Down
21 changes: 21 additions & 0 deletions util/osutil/os.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,32 @@ import (
"os"
"os/exec"
"path/filepath"
"strconv"
"strings"

"github.com/sirupsen/logrus"
)

// EnvVar is environment variable
type EnvVar string

// Exists checks if the environment variable has been set.
func (e EnvVar) Exists() bool {
_, ok := os.LookupEnv(string(e))
return ok
}

// Bool returns the environment variable value as boolean.
func (e EnvVar) Bool() bool {
ok, _ := strconv.ParseBool(e.Val())
return ok
}

// Bool returns the environment variable value.
func (e EnvVar) Val() string {
return os.Getenv(string(e))
}

const EnvColimaBinary = "COLIMA_BINARY"

// Executable returns the path name for the executable that started
Expand Down