diff --git a/internal/boxcli/generate.go b/internal/boxcli/generate.go index 3c9b5b265ab..7a96229eb00 100644 --- a/internal/boxcli/generate.go +++ b/internal/boxcli/generate.go @@ -24,6 +24,7 @@ type generateCmdFlags struct { force bool printEnvrcContent bool rootUser bool + envrcDir string // only used by generate direnv command } type generateDockerfileCmdFlags struct { @@ -147,10 +148,22 @@ func direnvCmd() *cobra.Command { command.Flags().BoolVarP( &flags.force, "force", "f", false, "force overwrite existing files") command.Flags().BoolVarP( - &flags.printEnvrcContent, "print-envrc", "p", false, "output contents of devbox configuration to use in .envrc") + &flags.printEnvrcContent, "print-envrc", "p", false, + "output contents of devbox configuration to use in .envrc") // this command marks a flag as hidden. Error handling for it is not necessary. _ = command.Flags().MarkHidden("print-envrc") + // --envrc-dir allows users to specify a directory where the .envrc file should be generated + // separately from the devbox config directory. Without this flag, the .envrc file + // will be generated in the same directory as the devbox config file (i.e., either the current + // directory or the directory specified by --config). This flag is useful for users who want to + // keep their .envrc and devbox config files in different locations. + command.Flags().StringVar( + &flags.envrcDir, "envrc-dir", "", + "path to directory where the .envrc file should be generated.\n"+ + "If not specified, the .envrc file will be generated in the same directory as\n"+ + "the devbox.json.") + flags.config.register(command) return command } @@ -266,9 +279,17 @@ func runGenerateCmd(cmd *cobra.Command, flags *generateCmdFlags) error { } func runGenerateDirenvCmd(cmd *cobra.Command, flags *generateCmdFlags) error { + // --print-envrc is used within the .envrc file and therefore doesn't make sense to also + // use it with --envrc-dir, which specifies a directory where the .envrc file should be generated. + if flags.printEnvrcContent && flags.envrcDir != "" { + return usererr.New( + "Cannot use --print-envrc with --envrc-dir. " + + "Use --envrc-dir to specify the directory where the .envrc file should be generated.") + } + if flags.printEnvrcContent { return devbox.PrintEnvrcContent( - cmd.OutOrStdout(), devopt.EnvFlags(flags.envFlag)) + cmd.OutOrStdout(), devopt.EnvFlags(flags.envFlag), flags.config.path) } box, err := devbox.Open(&devopt.Opts{ @@ -280,6 +301,12 @@ func runGenerateDirenvCmd(cmd *cobra.Command, flags *generateCmdFlags) error { return errors.WithStack(err) } - return box.GenerateEnvrcFile( - cmd.Context(), flags.force, devopt.EnvFlags(flags.envFlag)) + generateEnvrcOpts := devopt.EnvrcOpts{ + EnvFlags: devopt.EnvFlags(flags.envFlag), + Force: flags.force, + EnvrcDir: flags.envrcDir, + ConfigDir: flags.config.path, + } + + return box.GenerateEnvrcFile(cmd.Context(), generateEnvrcOpts) } diff --git a/internal/devbox/devbox.go b/internal/devbox/devbox.go index 22a1d22e3de..d65ba219352 100644 --- a/internal/devbox/devbox.go +++ b/internal/devbox/devbox.go @@ -527,21 +527,28 @@ func (d *Devbox) GenerateDockerfile(ctx context.Context, generateOpts devopt.Gen })) } -func PrintEnvrcContent(w io.Writer, envFlags devopt.EnvFlags) error { - return generate.EnvrcContent(w, envFlags) +func PrintEnvrcContent(w io.Writer, envFlags devopt.EnvFlags, configDir string) error { + return generate.EnvrcContent(w, envFlags, configDir) } // GenerateEnvrcFile generates a .envrc file that makes direnv integration convenient -func (d *Devbox) GenerateEnvrcFile(ctx context.Context, force bool, envFlags devopt.EnvFlags) error { +func (d *Devbox) GenerateEnvrcFile(ctx context.Context, opts devopt.EnvrcOpts) error { ctx, task := trace.NewTask(ctx, "devboxGenerateEnvrc") defer task.End() - envrcfilePath := filepath.Join(d.projectDir, ".envrc") - filesExist := fileutil.Exists(envrcfilePath) - if !force && filesExist { + // If no envrcDir was specified, use the configDir. This is for backward compatibility + // where the .envrc was placed in the same location as specified by --config. Note that + // if that is also blank, the .envrc will be generated in the current working directory. + if opts.EnvrcDir == "" { + opts.EnvrcDir = opts.ConfigDir + } + + envrcFilePath := filepath.Join(opts.EnvrcDir, ".envrc") + filesExist := fileutil.Exists(envrcFilePath) + if !opts.Force && filesExist { return usererr.New( - "A .envrc is already present in the current directory. " + - "Remove it or use --force to overwrite it.", + "A .envrc is already present in %q. Remove it or use --force to overwrite it.", + opts.EnvrcDir, ) } @@ -551,18 +558,18 @@ func (d *Devbox) GenerateEnvrcFile(ctx context.Context, force bool, envFlags dev } // .envrc file creation - err := generate.CreateEnvrc(ctx, d.projectDir, envFlags) + err := generate.CreateEnvrc(ctx, opts) if err != nil { return errors.WithStack(err) } - ux.Fsuccessf(d.stderr, "generated .envrc file\n") + ux.Fsuccessf(d.stderr, "generated .envrc file in %q.\n", opts.EnvrcDir) if cmdutil.Exists("direnv") { - cmd := exec.Command("direnv", "allow") + cmd := exec.Command("direnv", "allow", opts.EnvrcDir) err := cmd.Run() if err != nil { return errors.WithStack(err) } - ux.Fsuccessf(d.stderr, "ran `direnv allow`\n") + ux.Fsuccessf(d.stderr, "ran `direnv allow %s`\n", opts.EnvrcDir) } return nil } diff --git a/internal/devbox/devopt/devboxopts.go b/internal/devbox/devopt/devboxopts.go index b59759fe567..6ae164566c8 100644 --- a/internal/devbox/devopt/devboxopts.go +++ b/internal/devbox/devopt/devboxopts.go @@ -34,6 +34,13 @@ type EnvFlags struct { EnvFile string } +type EnvrcOpts struct { + EnvFlags + Force bool + EnvrcDir string + ConfigDir string +} + type PullboxOpts struct { Overwrite bool URL string diff --git a/internal/devbox/generate/devcontainer_util.go b/internal/devbox/generate/devcontainer_util.go index 7a99372f35f..1c6152d552f 100644 --- a/internal/devbox/generate/devcontainer_util.go +++ b/internal/devbox/generate/devcontainer_util.go @@ -140,11 +140,11 @@ func (g *Options) CreateDevcontainer(ctx context.Context) error { return err } -func CreateEnvrc(ctx context.Context, path string, envFlags devopt.EnvFlags) error { +func CreateEnvrc(ctx context.Context, opts devopt.EnvrcOpts) error { defer trace.StartRegion(ctx, "createEnvrc").End() // create .envrc file - file, err := os.Create(filepath.Join(path, ".envrc")) + file, err := os.Create(filepath.Join(opts.EnvrcDir, ".envrc")) if err != nil { return err } @@ -152,23 +152,56 @@ func CreateEnvrc(ctx context.Context, path string, envFlags devopt.EnvFlags) err flags := []string{} - if len(envFlags.EnvMap) > 0 { - for k, v := range envFlags.EnvMap { + if len(opts.EnvMap) > 0 { + for k, v := range opts.EnvMap { flags = append(flags, fmt.Sprintf("--env %s=%s", k, v)) } } - if envFlags.EnvFile != "" { - flags = append(flags, fmt.Sprintf("--env-file %s", envFlags.EnvFile)) + if opts.EnvFile != "" { + flags = append(flags, fmt.Sprintf("--env-file %s", opts.EnvFile)) + } + + configDir, err := getRelativePathToConfig(opts.EnvrcDir, opts.ConfigDir) + if err != nil { + return err } t := template.Must(template.ParseFS(tmplFS, "tmpl/envrc.tmpl")) // write content into file return t.Execute(file, map[string]string{ - "Flags": strings.Join(flags, " "), + "EnvFlag": strings.Join(flags, " "), + "ConfigDir": formatConfigDirArg(configDir), }) } +// Returns the relative path from sourceDir to configDir, or an error if it cannot be determined. +func getRelativePathToConfig(sourceDir string, configDir string) (string, error) { + absConfigDir, err := filepath.Abs(configDir) + if err != nil { + return "", fmt.Errorf("failed to get absolute path for config dir: %w", err) + } + + absSourceDir, err := filepath.Abs(sourceDir) + if err != nil { + return "", fmt.Errorf("failed to get absolute path for source dir: %w", err) + } + + // We don't want the path if the config dir is a parent of the envrc dir. This way + // the config will be found when it recursively searches for it through the parent tree. + if strings.HasPrefix(absSourceDir, absConfigDir) { + return "", nil + } + + relPath, err := filepath.Rel(absSourceDir, absConfigDir) + if err != nil { + // If a relative path cannot be computed, return the absolute path of configDir + return absConfigDir, nil + } + + return relPath, nil +} + func (g *Options) getDevcontainerContent() *devcontainerObject { // object that gets written in devcontainer.json devcontainerContent := &devcontainerObject{ @@ -219,17 +252,26 @@ func (g *Options) getDevcontainerContent() *devcontainerObject { return devcontainerContent } -func EnvrcContent(w io.Writer, envFlags devopt.EnvFlags) error { - tmplName := "envrcContent.tmpl" - t := template.Must(template.ParseFS(tmplFS, "tmpl/"+tmplName)) +func EnvrcContent(w io.Writer, envFlags devopt.EnvFlags, configDir string) error { + t := template.Must(template.ParseFS(tmplFS, "tmpl/envrcContent.tmpl")) envFlag := "" if len(envFlags.EnvMap) > 0 { for k, v := range envFlags.EnvMap { envFlag += fmt.Sprintf("--env %s=%s ", k, v) } } + return t.Execute(w, map[string]string{ - "EnvFlag": envFlag, - "EnvFile": envFlags.EnvFile, + "EnvFlag": envFlag, + "EnvFile": envFlags.EnvFile, + "ConfigDir": formatConfigDirArg(configDir), }) } + +func formatConfigDirArg(configDir string) string { + if configDir == "" { + return "" + } + + return "--config " + configDir +} diff --git a/internal/devbox/generate/tmpl/envrc.tmpl b/internal/devbox/generate/tmpl/envrc.tmpl index 98d6c927a85..d421ca3a72a 100644 --- a/internal/devbox/generate/tmpl/envrc.tmpl +++ b/internal/devbox/generate/tmpl/envrc.tmpl @@ -3,7 +3,7 @@ # Automatically sets up your devbox environment whenever you cd into this # directory via our direnv integration: -eval "$(devbox generate direnv --print-envrc{{ if .Flags}} {{ .Flags }}{{ end }})" +eval "$(devbox generate direnv --print-envrc{{ if .EnvFlag}} {{ .EnvFlag }}{{ end }}{{ if .ConfigDir }} {{ .ConfigDir }}{{ end }})" # check out https://www.jetpack.io/devbox/docs/ide_configuration/direnv/ # for more details diff --git a/internal/devbox/generate/tmpl/envrcContent.tmpl b/internal/devbox/generate/tmpl/envrcContent.tmpl index 80538b81d46..b68bbbc7204 100644 --- a/internal/devbox/generate/tmpl/envrcContent.tmpl +++ b/internal/devbox/generate/tmpl/envrcContent.tmpl @@ -1,6 +1,6 @@ use_devbox() { - watch_file devbox.json devbox.lock - eval "$(devbox shellenv --init-hook --install --no-refresh-alias{{ if .EnvFlag }} {{ .EnvFlag }}{{ end }})" + eval "$(devbox shellenv --init-hook --install --no-refresh-alias{{ if .EnvFlag }} {{ .EnvFlag }}{{ end }}{{ if .ConfigDir }} {{ .ConfigDir }}{{ end }})" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock } use devbox {{ if .EnvFile }} diff --git a/testscripts/generate/direnv-config-envflag.test.txt b/testscripts/generate/direnv-config-envflag.test.txt new file mode 100644 index 00000000000..dc5c9194b04 --- /dev/null +++ b/testscripts/generate/direnv-config-envflag.test.txt @@ -0,0 +1,26 @@ +# Testscript to validate generating the contents of the .envrc file. +# Note that since --envrc-dir was NOT specified, the .envrc will be in the `dir` directory and +# the config will be found there, which means the `--print-env` doesn't need to specify the dir. +# This matches the mode of operation prior to the addition of the --envrc-dir flag. + +mkdir dir +exec devbox init dir +exists dir/devbox.json + +exec devbox generate direnv --env x=y --config dir +grep 'eval "\$\(devbox generate direnv --print-envrc --env x=y\)"' dir/.envrc + +cd dir +exec devbox generate direnv --print-envrc --env x=y + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --env x=y )" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-config.test.txt b/testscripts/generate/direnv-config.test.txt new file mode 100644 index 00000000000..0211b3ff4ec --- /dev/null +++ b/testscripts/generate/direnv-config.test.txt @@ -0,0 +1,26 @@ +# Testscript to validate generating the contents of the .envrc file. +# Note that since --envrc-dir was NOT specified, the .envrc will be in the `dir` directory and +# the config will be found there, which means the `--print-env` doesn't need to specify the dir. +# This matches the mode of operation prior to the addition of the --envrc-dir flag. + +mkdir dir +exec devbox init dir +exists dir/devbox.json + +exec devbox generate direnv --config dir +grep 'eval "\$\(devbox generate direnv --print-envrc\)"' dir/.envrc + +cd dir +exec devbox generate direnv --print-envrc + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envflag.test.txt b/testscripts/generate/direnv-envflag.test.txt new file mode 100644 index 00000000000..2dd0aea9ff5 --- /dev/null +++ b/testscripts/generate/direnv-envflag.test.txt @@ -0,0 +1,21 @@ +# Testscript to validate generating the contents of the .envrc file. + +exec devbox init +exists devbox.json + +exec devbox generate direnv --env x=y +grep 'eval "\$\(devbox generate direnv --print-envrc --env x=y\)"' .envrc + +exec devbox generate direnv --print-envrc --env x=y + +cmp stdout expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --env x=y )" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-config-parent.test.txt b/testscripts/generate/direnv-envrcdir-config-parent.test.txt new file mode 100644 index 00000000000..161e14dff83 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-config-parent.test.txt @@ -0,0 +1,27 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./dir). +# The devbox config is in the current dir (parent to ./dir). Since no --config +# is specified, the normal config-finding will find the config. + +exec devbox init +exists ./devbox.json + +mkdir dir + +exec devbox generate direnv --envrc-dir dir +grep 'eval "\$\(devbox generate direnv --print-envrc\)"' dir/.envrc +! grep '--config' dir/.envrc # redundant, but making expectations obvious + +cd dir +exec devbox generate direnv --print-envrc + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-config-sibling.test.txt b/testscripts/generate/direnv-envrcdir-config-sibling.test.txt new file mode 100644 index 00000000000..0e48471de7b --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-config-sibling.test.txt @@ -0,0 +1,25 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./dir) that also +# references a devbox config in another dir (./cfg) that is a sibling to the first. + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +mkdir dir +exec devbox generate direnv --envrc-dir dir --config cfg +grep 'eval "\$\(devbox generate direnv --print-envrc --config ../cfg\)"' dir/.envrc + +cd dir +exec devbox generate direnv --print-envrc --config ../cfg + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --config ../cfg)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-config-subdir-envflag.test.txt b/testscripts/generate/direnv-envrcdir-config-subdir-envflag.test.txt new file mode 100644 index 00000000000..2dcab6115e1 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-config-subdir-envflag.test.txt @@ -0,0 +1,24 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./dir) that also +# references a devbox config in another dir (./dir/cfg) that is a subdir of the first. + +mkdir dir/cfg +exec devbox init dir/cfg +exists dir/cfg/devbox.json + +exec devbox generate direnv --envrc-dir dir --config dir/cfg --env x=y +grep 'eval "\$\(devbox generate direnv --print-envrc --env x=y --config cfg\)"' dir/.envrc + +cd dir +exec devbox generate direnv --print-envrc --env x=y --config cfg + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --env x=y --config cfg)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-config-subdir.test.txt b/testscripts/generate/direnv-envrcdir-config-subdir.test.txt new file mode 100644 index 00000000000..83dbcd001fd --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-config-subdir.test.txt @@ -0,0 +1,24 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./dir) that also +# references a devbox config in another dir (./dir/cfg) that is a subdir of the first. + +mkdir dir/cfg +exec devbox init dir/cfg +exists dir/cfg/devbox.json + +exec devbox generate direnv --envrc-dir dir --config dir/cfg +grep 'eval "\$\(devbox generate direnv --print-envrc --config cfg\)"' dir/.envrc + +cd dir +exec devbox generate direnv --print-envrc --config cfg + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --config cfg)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-current-config-sub.test.txt b/testscripts/generate/direnv-envrcdir-current-config-sub.test.txt new file mode 100644 index 00000000000..0d6533486b7 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-current-config-sub.test.txt @@ -0,0 +1,23 @@ +# Testscript to validate generating a direnv .envrc in the current location that +# references a devbox config in a subdir (./cfg). + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +exec devbox generate direnv --envrc-dir . --config cfg +grep 'eval "\$\(devbox generate direnv --print-envrc --config cfg\)"' ./.envrc + +exec devbox generate direnv --print-envrc --config cfg + +cmp stdout expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --config cfg)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir-fail-no-config.test.txt b/testscripts/generate/direnv-envrcdir-fail-no-config.test.txt new file mode 100644 index 00000000000..0696987fd66 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-fail-no-config.test.txt @@ -0,0 +1,9 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./cfg) that also +# contains a config, but NO --config is specified so it fails to find it. + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +! exec devbox generate direnv --envrc-dir cfg +stderr 'no devbox.json found in the current directory \(or any parent directories\). Did you run `devbox init` yet\?' diff --git a/testscripts/generate/direnv-envrcdir-parent-no-config.test.txt b/testscripts/generate/direnv-envrcdir-parent-no-config.test.txt new file mode 100644 index 00000000000..047b226d907 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-parent-no-config.test.txt @@ -0,0 +1,11 @@ +# Testscript to validate generating a direnv .envrc in the parent of the current +# dir. The devbox config is located in a sub dir, so from the parent dir, +# devbox will not be able to search "up" to find it. + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +mkdir dir +! exec devbox generate direnv --envrc-dir dir +stderr 'Error: no devbox.json found in the current directory \(or any parent directories\). Did you run `devbox init` yet\?' diff --git a/testscripts/generate/direnv-envrcdir-parent.test.txt b/testscripts/generate/direnv-envrcdir-parent.test.txt new file mode 100644 index 00000000000..a49a6424a93 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir-parent.test.txt @@ -0,0 +1,26 @@ +# Testscript to validate generating a direnv .envrc in the parent of the current +# dir, which is where the devbox config is located. + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +cd cfg + +exec devbox generate direnv --envrc-dir .. +grep 'eval "\$\(devbox generate direnv --print-envrc --config cfg\)"' ../.envrc + +cd .. +exec devbox generate direnv --print-envrc --config cfg + +cmp stdout expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --config cfg)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-envrcdir.test.txt b/testscripts/generate/direnv-envrcdir.test.txt new file mode 100644 index 00000000000..43cae344ce5 --- /dev/null +++ b/testscripts/generate/direnv-envrcdir.test.txt @@ -0,0 +1,27 @@ +# Testscript to validate generating a direnv .envrc in a specified location (./cfg) that also +# contains a devbox config in the same location. --config is required as the +# target dir is a subdir to the current dir which means the normal config-finding +# would not find it. + +mkdir cfg +exec devbox init cfg +exists cfg/devbox.json + +exec devbox generate direnv --envrc-dir cfg --config cfg +grep 'eval "\$\(devbox generate direnv --print-envrc\)"' cfg/.envrc +! grep '--config' cfg/.envrc + +cd cfg +exec devbox generate direnv --print-envrc + +cmp stdout ../expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-printenvrc-config.test.txt b/testscripts/generate/direnv-printenvrc-config.test.txt new file mode 100644 index 00000000000..89182a07f2c --- /dev/null +++ b/testscripts/generate/direnv-printenvrc-config.test.txt @@ -0,0 +1,21 @@ +# Testscript to validate generating the contents of the .envrc file. + +mkdir config-dir +exec devbox init config-dir +exists config-dir/devbox.json + +exec devbox generate direnv --print-envrc --config config-dir + +cmp stdout expected-results.txt + +! exists .envrc + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias --config config-dir)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv-printenvrc-envrcdir.test.txt b/testscripts/generate/direnv-printenvrc-envrcdir.test.txt new file mode 100644 index 00000000000..57ba3295b92 --- /dev/null +++ b/testscripts/generate/direnv-printenvrc-envrcdir.test.txt @@ -0,0 +1,8 @@ +# Testscript to validate that the --print-envrc and --envrc-dir params are not allowed +# to be used at the same time. + +exec devbox init +exists ./devbox.json + +! exec devbox generate direnv --print-envrc --envrc-dir dir +stderr 'Cannot use --print-envrc with --envrc-dir' \ No newline at end of file diff --git a/testscripts/generate/direnv-printenvrc.test.txt b/testscripts/generate/direnv-printenvrc.test.txt new file mode 100644 index 00000000000..9c66cda6302 --- /dev/null +++ b/testscripts/generate/direnv-printenvrc.test.txt @@ -0,0 +1,20 @@ +# Testscript to validate the output of --print-envrc + +exec devbox init +exists ./devbox.json + +exec devbox generate direnv --print-envrc + +cmp stdout expected-results.txt + +! exists .envrc + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox + diff --git a/testscripts/generate/direnv.test.txt b/testscripts/generate/direnv.test.txt index 3863a7915e8..f09a0d2b893 100644 --- a/testscripts/generate/direnv.test.txt +++ b/testscripts/generate/direnv.test.txt @@ -1,4 +1,21 @@ +# Testscript to validate generating the contents of the .envrc file. + exec devbox init +exists ./devbox.json + exec devbox generate direnv -exists .envrc +grep 'eval "\$\(devbox generate direnv --print-envrc\)"' .envrc + +exec devbox generate direnv --print-envrc + +cmp stdout expected-results.txt + +# Note: The contents of the following file ends with two blank lines. This is +# necessary to match the blank line that follows "use devbox" in the actual output. +-- expected-results.txt -- +use_devbox() { + eval "$(devbox shellenv --init-hook --install --no-refresh-alias)" + watch_file $DEVBOX_PROJECT_ROOT/devbox.json $DEVBOX_PROJECT_ROOT/devbox.lock +} +use devbox