diff --git a/pkg/limatmpl/abs.go b/pkg/limatmpl/abs.go index 2598b377c5f..bfc7060e9e5 100644 --- a/pkg/limatmpl/abs.go +++ b/pkg/limatmpl/abs.go @@ -11,6 +11,8 @@ import ( "path/filepath" "runtime" "strings" + + "github.com/lima-vm/lima/v2/pkg/localpathutil" ) // UseAbsLocators will replace all relative template locators with absolute ones, so this template @@ -105,6 +107,13 @@ func absPath(locator, basePath string) (string, error) { if err == nil && len(u.Scheme) > 1 { return locator, nil } + // Don't expand relative path to absolute. Tilde paths however are absolute paths already. + if localpathutil.IsTildePath(locator) { + locator, err = localpathutil.Expand(locator) + if err != nil { + return "", err + } + } // Check for rooted locator; filepath.IsAbs() returns false on Windows when the volume name is missing volumeLen := len(filepath.VolumeName(locator)) if locator[volumeLen] != '/' && locator[volumeLen] != filepath.Separator { diff --git a/pkg/limatmpl/abs_test.go b/pkg/limatmpl/abs_test.go index fbf7c19bca4..5b78e9c155b 100644 --- a/pkg/limatmpl/abs_test.go +++ b/pkg/limatmpl/abs_test.go @@ -4,6 +4,7 @@ package limatmpl import ( + "os" "path/filepath" "runtime" "strings" @@ -205,6 +206,15 @@ func TestAbsPath(t *testing.T) { assert.Equal(t, actual, filepath.Clean(volume+"/foo")) }) + t.Run("If the locator starts with ~/, then it will be expanded to an absolute path", func(t *testing.T) { + actual, err := absPath("~/foo", volume+"/root") + assert.NilError(t, err) + homeDir, err := os.UserHomeDir() + assert.NilError(t, err) + // homeDir already includes the volume + assert.Equal(t, actual, filepath.Join(homeDir, "foo")) + }) + t.Run("", func(t *testing.T) { actual, err := absPath("template://foo", volume+"/root") assert.NilError(t, err) diff --git a/pkg/localpathutil/localpathutil.go b/pkg/localpathutil/localpathutil.go index 3081763b159..baa4ceb1f71 100644 --- a/pkg/localpathutil/localpathutil.go +++ b/pkg/localpathutil/localpathutil.go @@ -11,6 +11,12 @@ import ( "strings" ) +// IsTildePath returns true if the path is "~" or starts with "~/". +// This means Expand() can expand it with the home directory. +func IsTildePath(path string) bool { + return path == "~" || strings.HasPrefix(path, "~/") +} + // Expand expands a path like "~", "~/", "~/foo". // Paths like "~foo/bar" are unsupported. // @@ -20,13 +26,13 @@ func Expand(orig string) (string, error) { if s == "" { return "", errors.New("empty path") } - homeDir, err := os.UserHomeDir() - if err != nil { - return "", err - } if strings.HasPrefix(s, "~") { - if s == "~" || strings.HasPrefix(s, "~/") { + if IsTildePath(s) { + homeDir, err := os.UserHomeDir() + if err != nil { + return "", err + } s = strings.Replace(s, "~", homeDir, 1) } else { // Paths like "~foo/bar" are unsupported.