Hello community, here is the log from the commit of package direnv for openSUSE:Factory checked in at 2020-08-21 19:04:13 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/direnv (Old) and /work/SRC/openSUSE:Factory/.direnv.new.3399 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "direnv" Fri Aug 21 19:04:13 2020 rev:7 rq:828194 version:2.21.3 Changes: -------- --- /work/SRC/openSUSE:Factory/direnv/direnv.changes 2020-05-14 23:27:34.201344412 +0200 +++ /work/SRC/openSUSE:Factory/.direnv.new.3399/direnv.changes 2020-08-21 19:04:58.688384755 +0200 @@ -1,0 +2,30 @@ +Wed Aug 19 09:07:53 UTC 2020 - Dirk Mueller <dmuel...@suse.com> + +- update to 2.21.3: + * Replace direnv expand_path with pure bash (#631) + * Fix #594 - write error to fd 3 on Windows (#634) + * Make direnv hook output work on Windows (#632) + * Update hook.md to remove ">" typo in Fish instructions (#624) + * stdlib: layout go adds layout dir to GOPATH (#622) + * direnv-stdlib.1: add layout php (#619) + * stdlib: add PATH_rm [ ...] (#615) + * Error handling tuples (#610) + * Merge pull request #607 from punitagrawal/master + * test: elvish: Fix evaluation function + * stdlib.sh: Re-write grep pattern to avoid shell escape + * man: Escape '.' at the beginning of line to remove manpage warning + * stdlib: fix direnv_config_dir usage (#601) + * direnv version: improve error message (#599) + * README: fix NixOS link in installation.md (#589) + * stdlib: add direnv_apply_dump (#587) + * Simplify direnv_load and make it work even when the command crashes. (#568) + * docs: fix fish installation instruction + * test: test for utf-8 compatibility + * config: add [global] section + * config: add strict_env option + * config: fix warn_timeout parsing (#582) + * Github action for releases + * config: fix the configuration file selection + * stdlib: fix shellcheck warnings + +------------------------------------------------------------------- Old: ---- direnv-2.21.2.tar.gz New: ---- direnv-2.21.3.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ direnv.spec ++++++ --- /var/tmp/diff_new_pack.1ygzgs/_old 2020-08-21 19:05:00.448385801 +0200 +++ /var/tmp/diff_new_pack.1ygzgs/_new 2020-08-21 19:05:00.452385803 +0200 @@ -18,7 +18,7 @@ %define gopackagepath github.com/direnv/direnv Name: direnv -Version: 2.21.2 +Version: 2.21.3 Release: 0 Summary: Environment switcher for shells License: MIT ++++++ direnv-2.21.2.tar.gz -> direnv-2.21.3.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/.github/workflows/release.yml new/direnv-2.21.3/.github/workflows/release.yml --- old/direnv-2.21.2/.github/workflows/release.yml 1970-01-01 01:00:00.000000000 +0100 +++ new/direnv-2.21.3/.github/workflows/release.yml 2020-05-08 15:58:17.000000000 +0200 @@ -0,0 +1,37 @@ +on: + push: + # Sequence of patterns matched against refs/tags + tags: + - 'v*' # Push events to matching v*, i.e. v1.0, v20.15.10 + +# TODO: also publish the dist +name: Create Release + +jobs: + build: + name: Create Release + runs-on: ubuntu-latest + steps: + - name: Set up Go 1.13.6 + uses: actions/setup-go@v1 + with: + go-version: 1.13.6 + - name: Checkout code + uses: actions/checkout@master + - name: Get release notes + id: release-notes + run: | + go run ./script/issue-command/main.go set-output \ + --name=body \ + "$(go run ./script/release-changelog/main.go)" + - name: Create Release + id: create_release + uses: actions/create-release@v1 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + tag_name: ${{ github.ref }} + release_name: Release ${{ github.ref }} + body: "${{ steps.release-notes.outputs.body }}" + draft: true + prerelease: false diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/CHANGELOG.md new/direnv-2.21.3/CHANGELOG.md --- old/direnv-2.21.2/CHANGELOG.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/CHANGELOG.md 2020-05-08 15:58:17.000000000 +0200 @@ -1,3 +1,33 @@ + +2.21.3 / 2020-05-08 +================== + + * Replace `direnv expand_path` with pure bash (#631) + * Fix #594 - write error to fd 3 on Windows (#634) + * Make direnv hook output work on Windows (#632) + * Update hook.md to remove ">" typo in Fish instructions (#624) + * stdlib: `layout go` adds layout dir to GOPATH (#622) + * direnv-stdlib.1: add layout php (#619) + * stdlib: add PATH_rm <pattern> [<pattern> ...] (#615) + * Error handling tuples (#610) + * Merge pull request #607 from punitagrawal/master + * test: elvish: Fix evaluation function + * stdlib.sh: Re-write grep pattern to avoid shell escape + * man: Escape '.' at the beginning of line to remove manpage warning + * stdlib: fix direnv_config_dir usage (#601) + * direnv version: improve error message (#599) + * README: fix NixOS link in installation.md (#589) + * stdlib: add direnv_apply_dump <file> (#587) + * Simplify direnv_load and make it work even when the command crashes. (#568) + * docs: fix fish installation instruction + * test: test for utf-8 compatibility + * config: add [global] section + * config: add strict_env option + * config: fix warn_timeout parsing (#582) + * Github action for releases + * config: fix the configuration file selection + * stdlib: fix shellcheck warnings + 2.21.2 / 2020-01-28 ================== diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_allow.go new/direnv-2.21.3/cmd_allow.go --- old/direnv-2.21.2/cmd_allow.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_allow.go 2020-05-08 15:58:17.000000000 +0200 @@ -55,8 +55,10 @@ } } - rc := FindRC(rcPath, config) - if rc == nil { + rc, err := FindRC(rcPath, config) + if err != nil { + return err + } else if rc == nil { return fmt.Errorf(".envrc file not found") } return rc.Allow() diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_deny.go new/direnv-2.21.3/cmd_deny.go --- old/direnv-2.21.2/cmd_deny.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_deny.go 2020-05-08 15:58:17.000000000 +0200 @@ -24,8 +24,10 @@ } } - rc := FindRC(rcPath, config) - if rc == nil { + rc, err := FindRC(rcPath, config) + if err != nil { + return err + } else if rc == nil { return fmt.Errorf(".envrc file not found") } return rc.Deny() diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_edit.go new/direnv-2.21.3/cmd_edit.go --- old/direnv-2.21.2/cmd_edit.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_edit.go 2020-05-08 15:58:17.000000000 +0200 @@ -26,7 +26,10 @@ defer log.SetPrefix(log.Prefix()) log.SetPrefix(log.Prefix() + "cmd_edit: ") - foundRC = config.FindRC() + foundRC, err = config.FindRC() + if err != nil { + return err + } if foundRC != nil { times = &foundRC.times } @@ -64,13 +67,13 @@ return } - foundRC = FindRC(rcPath, config) + foundRC, err = FindRC(rcPath, config) logDebug("foundRC: %#v", foundRC) logDebug("times: %#v", times) if times != nil { logDebug("times.Check(): %#v", times.Check()) } - if foundRC != nil && (times == nil || times.Check() != nil) { + if err == nil && foundRC != nil && (times == nil || times.Check() != nil) { err = foundRC.Allow() } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_exec.go new/direnv-2.21.3/cmd_exec.go --- old/direnv-2.21.2/cmd_exec.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_exec.go 2020-05-08 15:58:17.000000000 +0200 @@ -46,7 +46,10 @@ args = args[1:] } - rc := FindRC(rcPath, config) + rc, err := FindRC(rcPath, config) + if err != nil { + return + } // Restore pristine environment if needed if backupDiff, err = config.EnvDiff(); err == nil && backupDiff != nil { diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_expand_path.go new/direnv-2.21.3/cmd_expand_path.go --- old/direnv-2.21.2/cmd_expand_path.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_expand_path.go 1970-01-01 01:00:00.000000000 +0100 @@ -1,59 +0,0 @@ -package main - -import ( - "flag" - "fmt" - "os" - "path/filepath" -) - -func expandPath(path, relTo string) string { - if filepath.IsAbs(path) { - return path - } - return filepath.Clean(filepath.Join(relTo, path)) -} - -// CmdExpandPath is `direnv expand_path PATH [REL_TO]` -var CmdExpandPath = &Cmd{ - Name: "expand_path", - Desc: "Transforms a PATH to an absolute path to REL_TO or $PWD", - Args: []string{"PATH", "[REL_TO]"}, - Private: true, - Action: actionSimple(cmdExpandPathAction), -} - -func cmdExpandPathAction(env Env, args []string) (err error) { - var path string - - flagset := flag.NewFlagSet(args[0], flag.ExitOnError) - err = flagset.Parse(args[1:]) - if err != nil { - return err - } - - path = flagset.Arg(0) - if path == "" { - return fmt.Errorf("PATH missing") - } - - if !filepath.IsAbs(path) { - wd, err := os.Getwd() - if err != nil { - return err - } - - relTo := flagset.Arg(1) - if relTo == "" { - relTo = wd - } else { - relTo = expandPath(relTo, wd) - } - - path = expandPath(path, relTo) - } - - _, err = fmt.Println(path) - - return -} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_export.go new/direnv-2.21.3/cmd_export.go --- old/direnv-2.21.2/cmd_export.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_export.go 2020-05-08 15:58:17.000000000 +0200 @@ -92,7 +92,7 @@ func (ec *ExportContext) getRCs() { ec.loadedRC = ec.config.LoadedRC() - ec.foundRC = ec.config.FindRC() + ec.foundRC, _ = ec.config.FindRC() } func (ec *ExportContext) hasRC() bool { diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_hook.go new/direnv-2.21.3/cmd_hook.go --- old/direnv-2.21.2/cmd_hook.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_hook.go 2020-05-08 15:58:17.000000000 +0200 @@ -3,6 +3,7 @@ import ( "fmt" "os" + "strings" "text/template" ) @@ -32,6 +33,8 @@ return err } + // Convert Windows path if needed + selfPath = strings.Replace(selfPath, "\\", "/", -1) ctx := HookContext{selfPath} shell := DetectShell(target) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_reload.go new/direnv-2.21.3/cmd_reload.go --- old/direnv-2.21.2/cmd_reload.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_reload.go 2020-05-08 15:58:17.000000000 +0200 @@ -9,7 +9,10 @@ Name: "reload", Desc: "triggers an env reload", Action: actionWithConfig(func(env Env, args []string, config *Config) error { - foundRC := config.FindRC() + foundRC, err := config.FindRC() + if err != nil { + return err + } if foundRC == nil { return fmt.Errorf(".envrc not found") } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_status.go new/direnv-2.21.3/cmd_status.go --- old/direnv-2.21.2/cmd_status.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_status.go 2020-05-08 15:58:17.000000000 +0200 @@ -20,7 +20,10 @@ fmt.Println("whitelist.exact", config.WhitelistExact) loadedRC := config.LoadedRC() - foundRC := config.FindRC() + foundRC, err := config.FindRC() + if err != nil { + return err + } if loadedRC != nil { formatRC("Loaded", loadedRC) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/cmd_version.go new/direnv-2.21.3/cmd_version.go --- old/direnv-2.21.2/cmd_version.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/cmd_version.go 2020-05-08 15:58:17.000000000 +0200 @@ -25,7 +25,7 @@ } cmp := semver.Compare(semVersion, atLeast) if cmp < 0 { - return fmt.Errorf("%s it older than the desired %s", semVersion, atLeast) + return fmt.Errorf("current version %s is older than the desired version %s", semVersion, atLeast) } } else { fmt.Println(Version) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/commands.go new/direnv-2.21.3/commands.go --- old/direnv-2.21.2/commands.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/commands.go 2020-05-08 15:58:17.000000000 +0200 @@ -53,7 +53,6 @@ CmdDump, CmdEdit, CmdExec, - CmdExpandPath, CmdExport, CmdHelp, CmdHook, diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/config.go new/direnv-2.21.3/config.go --- old/direnv-2.21.2/config.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/config.go 2020-05-08 15:58:17.000000000 +0200 @@ -23,19 +23,36 @@ RCDir string TomlPath string DisableStdin bool + StrictEnv bool WarnTimeout time.Duration WhitelistPrefix []string WhitelistExact map[string]bool } +type tomlDuration struct { + time.Duration +} + +func (d *tomlDuration) UnmarshalText(text []byte) error { + var err error + d.Duration, err = time.ParseDuration(string(text)) + return err +} + type tomlConfig struct { - BashPath string `toml:"bash_path"` - DisableStdin bool `toml:"disable_stdin"` - WarnTimeout time.Duration `toml:"warn_timeout"` - Whitelist whitelist `toml:"whitelist"` + *tomlGlobal // For backward-compatibility + Global *tomlGlobal `toml:"global"` + Whitelist tomlWhitelist `toml:"whitelist"` } -type whitelist struct { +type tomlGlobal struct { + BashPath string `toml:"bash_path"` + DisableStdin bool `toml:"disable_stdin"` + StrictEnv bool `toml:"strict_env"` + WarnTimeout tomlDuration `toml:"warn_timeout"` +} + +type tomlWhitelist struct { Prefix []string Exact []string } @@ -80,16 +97,21 @@ // Load the TOML config config.TomlPath = filepath.Join(config.ConfDir, "direnv.toml") if _, statErr := os.Stat(config.TomlPath); statErr != nil { - config.TomlPath = "" - } - - config.TomlPath = filepath.Join(config.ConfDir, "config.toml") - if _, statErr := os.Stat(config.TomlPath); statErr != nil { - config.TomlPath = "" + config.TomlPath = filepath.Join(config.ConfDir, "config.toml") + if _, statErr := os.Stat(config.TomlPath); statErr != nil { + config.TomlPath = "" + } } if config.TomlPath != "" { - var tomlConf tomlConfig + // Declare global once and then share it between the top-level and Global + // keys. The goal here is to let the decoder fill global regardless of if + // the values are in the [global] section or not. The reason we do that is + var global tomlGlobal + tomlConf := tomlConfig{ + tomlGlobal: &global, + Global: &global, + } if _, err = toml.DecodeFile(config.TomlPath, &tomlConf); err != nil { err = fmt.Errorf("LoadConfig() failed to parse %s: %q", config.TomlPath, err) return @@ -105,9 +127,10 @@ config.WhitelistExact[path] = true } - config.DisableStdin = tomlConf.DisableStdin config.BashPath = tomlConf.BashPath - config.WarnTimeout = tomlConf.WarnTimeout + config.DisableStdin = tomlConf.DisableStdin + config.StrictEnv = tomlConf.StrictEnv + config.WarnTimeout = tomlConf.WarnTimeout.Duration } if config.WarnTimeout == 0 { @@ -160,7 +183,7 @@ } // FindRC looks for a RC file in the config environment -func (config *Config) FindRC() *RC { +func (config *Config) FindRC() (*RC, error) { return FindRC(config.WorkDir, config) } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/docs/hook.md new/direnv-2.21.3/docs/hook.md --- old/direnv-2.21.2/docs/hook.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/docs/hook.md 2020-05-08 15:58:17.000000000 +0200 @@ -28,8 +28,8 @@ Add the following line at the end of the `~/.config/fish/config.fish` file: -```fish -direnv hook fish | source +```sh +eval (direnv hook fish) ``` ## TCSH diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/docs/installation.md new/direnv-2.21.3/docs/installation.md --- old/direnv-2.21.2/docs/installation.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/docs/installation.md 2020-05-08 15:58:17.000000000 +0200 @@ -14,7 +14,7 @@ * [Debian](https://packages.debian.org/search?keywords=direnv&searchon=names&suite=all§ion=all) * [Gentoo go-overlay](https://github.com/Dr-Terrible/go-overlay) * [NetBSD pkgsrc-wip](http://www.pkgsrc.org/wip/) -* [NixOS](https://nixos.org/nixos/packages.html#direnv) +* [NixOS](https://nixos.org/nixos/packages.html?query=direnv) * [OSX Homebrew](http://brew.sh/) * [openSUSE](https://build.opensuse.org/package/show/openSUSE%3AFactory/direnv) * [MacPorts](https://www.macports.org/) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv-stdlib.1 new/direnv-2.21.3/man/direnv-stdlib.1 --- old/direnv-2.21.2/man/direnv-stdlib.1 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv-stdlib.1 2020-05-08 15:58:17.000000000 +0200 @@ -108,6 +108,10 @@ .PP NOTE: the other \fB\fC\&.envrc\fR is not checked by the security framework. +.SS \fB\fCdirenv\_apply\_dump <file>\fR +.PP +Loads the output of \fB\fCdirenv dump\fR that was stored in a file. + .SS \fB\fCdirenv\_load [<command\-generating\-dump\-output>]\fR .PP Applies the environment generated by running \fIargv\fP as a command. This is useful for adopting the environment of a child process \- cause that process to run "direnv dump" and then wrap the results with direnv\_load. @@ -152,6 +156,31 @@ .PP Works like \fB\fCPATH\_add\fR except that it's for an arbitrary \fIvarname\fP\&. +.SS \fB\fCPATH\_rm <pattern> [<pattern> ...]\fR +.PP +Removes directories that match any of the given shell patterns from the PATH environment variable. Order of the remaining directories is preserved in the resulting PATH. + +.PP +Bash pattern syntax: + +\[la]https://www.gnu.org/software/bash/manual/html_node/Pattern-Matching.html\[ra] + +.PP +Example: + +.PP +.RS + +.nf +echo $PATH +# output: /dontremove/me:/remove/me:/usr/local/bin/:... +PATH\_rm '/remove/*' +echo $PATH +# output: /dontremove/me:/usr/local/bin/:... + +.fi +.RE + .SS \fB\fCload\_prefix <prefix\_path>\fR .PP Expands some common path variables for the given \fIprefix\_path\fP prefix. This is useful if you installed something in the \fIprefix\_path\fP using \fB\fC\&./configure \-\&\-\&prefix=$prefix\_\&path \&\&\&\& make install\fR and want to use it in the project. @@ -200,6 +229,10 @@ .PP Adds "$PWD/node\_modules/.bin" to the PATH environment variable. +.SS \fB\fClayout php\fR +.PP +Adds "$PWD/vendor/bin" to the PATH environment variable. + .SS \fB\fClayout perl\fR .PP Setup environment variables required by perl's local::lib See diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv-stdlib.1.md new/direnv-2.21.3/man/direnv-stdlib.1.md --- old/direnv-2.21.2/man/direnv-stdlib.1.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv-stdlib.1.md 2020-05-08 15:58:17.000000000 +0200 @@ -81,6 +81,10 @@ NOTE: the other `.envrc` is not checked by the security framework. +### `direnv_apply_dump <file>` + +Loads the output of `direnv dump` that was stored in a file. + ### `direnv_load [<command-generating-dump-output>]` Applies the environment generated by running *argv* as a command. This is useful for adopting the environment of a child process - cause that process to run "direnv dump" and then wrap the results with direnv_load. @@ -109,6 +113,22 @@ Works like `PATH_add` except that it's for an arbitrary *varname*. +### `PATH_rm <pattern> [<pattern> ...]` + +Removes directories that match any of the given shell patterns from the PATH environment variable. Order of the remaining directories is preserved in the resulting PATH. + +Bash pattern syntax: + https://www.gnu.org/software/bash/manual/html_node/Pattern-Matching.html + +Example: + + echo $PATH + # output: /dontremove/me:/remove/me:/usr/local/bin/:... + PATH_rm '/remove/*' + echo $PATH + # output: /dontremove/me:/usr/local/bin/:... + + ### `load_prefix <prefix_path>` Expands some common path variables for the given *prefix_path* prefix. This is useful if you installed something in the *prefix_path* using `./configure --prefix=$prefix_path && make install` and want to use it in the project. @@ -141,6 +161,10 @@ Adds "$PWD/node_modules/.bin" to the PATH environment variable. +### `layout php` + +Adds "$PWD/vendor/bin" to the PATH environment variable. + ### `layout perl` Setup environment variables required by perl's local::lib See http://search.cpan.org/dist/local-lib/lib/local/lib.pm for more details. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv.1 new/direnv-2.21.3/man/direnv.1 --- old/direnv-2.21.2/man/direnv.1 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv.1 2020-05-08 15:58:17.000000000 +0200 @@ -34,7 +34,7 @@ $ echo ${FOO\-nope} nope $ echo export FOO=foo > .envrc -.envrc is not allowed +\\.envrc is not allowed $ direnv allow . direnv: reloading direnv: loading .envrc diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv.1.md new/direnv-2.21.3/man/direnv.1.md --- old/direnv-2.21.2/man/direnv.1.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv.1.md 2020-05-08 15:58:17.000000000 +0200 @@ -36,7 +36,7 @@ $ echo ${FOO-nope} nope $ echo export FOO=foo > .envrc -.envrc is not allowed +\.envrc is not allowed $ direnv allow . direnv: reloading direnv: loading .envrc diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv.toml.1 new/direnv-2.21.3/man/direnv.toml.1 --- old/direnv-2.21.2/man/direnv.toml.1 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv.toml.1 2020-05-08 15:58:17.000000000 +0200 @@ -34,7 +34,21 @@ .PP The following sections are supported: -.SH \fB\fCwarn\_timeout\fR +.SH [global] +.SS \fB\fCbash\_path\fR +.PP +This allows one to hard\-code the position of bash. It maybe be useful to set this to avoid having direnv to fail when PATH is being mutated. + +.SS \fB\fCdisable\_stdin\fR +.PP +If set to \fB\fCtrue\fR, stdin is disabled (redirected to /dev/null) during the \fB\fC\&.envrc\fR evaluation. + +.SS \fB\fCstrict\_env\fR +.PP +If set to true, the \fB\fC\&.envrc\fR will be loaded with \fB\fCset \-euo pipefail\fR\&. This +option will be the default in the future. + +.SS \fB\fCwarn\_timeout\fR .PP Specify how long to wait before warning the user that the command is taking too long to execute. Defaults to "5s". @@ -44,7 +58,7 @@ optional fraction and a unit suffix, such as "300ms", "\-1.5h" or "2h45m". Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h". -.SH \fB\fCwhitelist\fR +.SH [whitelist] .PP Specifying whitelist directives marks specific directory hierarchies or specific directories as "trusted" \-\- direnv will evaluate any matching .envrc files regardless of whether they have been specifically allowed. \fBThis feature should be used with great care\fP, as anyone with the ability to write files to that directory (including collaborators on VCS repositories) will be able to execute arbitrary code on your computer. @@ -115,14 +129,6 @@ .IP \(bu 2 \fB\fC/home/user/code/.envrc\fR -.SH \fB\fCbash\_path\fR -.PP -This allows one to hard\-code the position of bash. It maybe be useful to set this to avoid having direnv to fail when PATH is being mutated. - -.SH \fB\fCdisable\_stdin\fR -.PP -If set to true, stdin is disabled (redirected to /dev/null) during the \fB\fC\&.envrc\fR evaluation. - .SH COPYRIGHT .PP MIT licence \- Copyright (C) 2019 @zimbatm and contributors diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/man/direnv.toml.1.md new/direnv-2.21.3/man/direnv.toml.1.md --- old/direnv-2.21.2/man/direnv.toml.1.md 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/man/direnv.toml.1.md 2020-05-08 15:58:17.000000000 +0200 @@ -30,7 +30,22 @@ The following sections are supported: -## `warn_timeout` +## [global] + +### `bash_path` + +This allows one to hard-code the position of bash. It maybe be useful to set this to avoid having direnv to fail when PATH is being mutated. + +### `disable_stdin` + +If set to `true`, stdin is disabled (redirected to /dev/null) during the `.envrc` evaluation. + +### `strict_env` + +If set to true, the `.envrc` will be loaded with `set -euo pipefail`. This +option will be the default in the future. + +### `warn_timeout` Specify how long to wait before warning the user that the command is taking too long to execute. Defaults to "5s". @@ -39,7 +54,7 @@ optional fraction and a unit suffix, such as "300ms", "-1.5h" or "2h45m". Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h". -## `whitelist` +## [whitelist] Specifying whitelist directives marks specific directory hierarchies or specific directories as "trusted" -- direnv will evaluate any matching .envrc files regardless of whether they have been specifically allowed. **This feature should be used with great care**, as anyone with the ability to write files to that directory (including collaborators on VCS repositories) will be able to execute arbitrary code on your computer. @@ -88,14 +103,6 @@ * `/home/user/code/project-b/subproject-c/.envrc` * `/home/user/code/.envrc` -## `bash_path` - -This allows one to hard-code the position of bash. It maybe be useful to set this to avoid having direnv to fail when PATH is being mutated. - -## `disable_stdin` - -If set to true, stdin is disabled (redirected to /dev/null) during the `.envrc` evaluation. - COPYRIGHT --------- diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/rc.go new/direnv-2.21.3/rc.go --- old/direnv-2.21.2/rc.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/rc.go 2020-05-08 15:58:17.000000000 +0200 @@ -22,20 +22,20 @@ } // FindRC looks the RC file from the wd, up to the root -func FindRC(wd string, config *Config) *RC { +func FindRC(wd string, config *Config) (*RC, error) { rcPath := findUp(wd, ".envrc") if rcPath == "" { - return nil + return nil, nil } return RCFromPath(rcPath, config) } // RCFromPath inits the RC from a given path -func RCFromPath(path string, config *Config) *RC { +func RCFromPath(path string, config *Config) (*RC, error) { hash, err := fileHash(path) if err != nil { - return nil + return nil, err } allowPath := filepath.Join(config.AllowDir(), hash) @@ -44,15 +44,15 @@ err = times.Update(path) if err != nil { - return nil + return nil, err } err = times.Update(allowPath) if err != nil { - return nil + return nil, err } - return &RC{path, allowPath, times, config} + return &RC{path, allowPath, times, config}, nil } // RCFromEnv inits the RC from the environment @@ -146,8 +146,14 @@ return } + prelude := "" + if config.StrictEnv { + prelude = "set -euo pipefail && " + } + arg := fmt.Sprintf( - `eval "$("%s" stdlib)" && __main__ source_env "%s"`, + `%seval "$("%s" stdlib)" && __main__ source_env "%s"`, + prelude, direnv, rc.Path(), ) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/script/issue-command/main.go new/direnv-2.21.3/script/issue-command/main.go --- old/direnv-2.21.2/script/issue-command/main.go 1970-01-01 01:00:00.000000000 +0100 +++ new/direnv-2.21.3/script/issue-command/main.go 2020-05-08 15:58:17.000000000 +0200 @@ -0,0 +1,56 @@ +package main + +import ( + "fmt" + "os" + "strings" +) + +func escapeData(data string) string { + data = strings.ReplaceAll(data, "%", "%25") + data = strings.ReplaceAll(data, "\r", "%0D") + data = strings.ReplaceAll(data, "\n", "%0A") + return data +} + +func escapeProperty(prop string) string { + prop = escapeData(prop) + prop = strings.ReplaceAll(prop, ":", "%3A") + prop = strings.ReplaceAll(prop, ",", "%2C") + return prop +} + +// Go implementation of +// https://github.com/actions/toolkit/blob/master/packages/core/src/command.ts +func main() { + var remain []string + var props []string + + for _, arg := range os.Args[1:] { + if arg == "--" { + continue + } + if strings.HasPrefix(arg, "--") { + kv := strings.SplitN(arg[2:], "=", 2) + if len(kv) != 2 { + panic(fmt.Sprintf("expected %s to be of form --key=value", arg[2:])) + } + props = append(props, fmt.Sprintf("%s=%s", kv[0], escapeProperty(kv[1]))) + } else { + remain = append(remain, arg) + } + } + + if len(remain) != 2 { + panic(fmt.Sprintf("expected 2 remaining arguments, go %v", remain)) + } + + cmd := remain[0] + msg := escapeData(remain[1]) + var propStr string + if len(props) > 0 { + propStr = " " + strings.Join(props, ",") + } + + fmt.Printf("::%s%s::%s", cmd, propStr, msg) +} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/script/release-changelog/main.go new/direnv-2.21.3/script/release-changelog/main.go --- old/direnv-2.21.2/script/release-changelog/main.go 1970-01-01 01:00:00.000000000 +0100 +++ new/direnv-2.21.3/script/release-changelog/main.go 2020-05-08 15:58:17.000000000 +0200 @@ -0,0 +1,46 @@ +package main + +import ( + "bufio" + "os" + "strings" +) + +func run() error { + headers := 0 + + f, err := os.Open("CHANGELOG.md") + if err != nil { + return err + } + + r := bufio.NewReader(f) + + prev, err := r.ReadString('\n') + if err != nil { + return err + } + + for { + line, err := r.ReadString('\n') + if err != nil { + return err + } + if strings.HasPrefix(line, "======") { + headers++ + } + if headers > 1 { + return nil + } + + os.Stdout.WriteString(prev) + prev = line + } +} + +func main() { + err := run() + if err != nil { + panic(err) + } +} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/stdlib.go new/direnv-2.21.3/stdlib.go --- old/direnv-2.21.2/stdlib.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/stdlib.go 2020-05-08 15:58:17.000000000 +0200 @@ -13,6 +13,7 @@ "# SC2059: Don't use variables in the printf format string. Use printf \"..%s..\" \"$foo\".\n" + "shopt -s gnu_errfmt\n" + "shopt -s nullglob\n" + + "shopt -s extglob\n" + "\n" + "\n" + "# NOTE: don't touch the RHS, it gets replaced at runtime\n" + @@ -22,7 +23,7 @@ "DIRENV_LOG_FORMAT=\"${DIRENV_LOG_FORMAT-direnv: %s}\"\n" + "\n" + "# Where direnv configuration should be stored\n" + - "direnv_config_dir=${XDG_CONFIG_DIR:-$HOME/.config}/direnv\n" + + "direnv_config_dir=${XDG_CONFIG_HOME:-$HOME/.config}/direnv\n" + "\n" + "# This variable can be used by programs to detect when they are running inside\n" + "# of a .envrc evaluation context. It is ignored by the direnv diffing\n" + @@ -118,9 +119,24 @@ "# # output: /usr/local/foo\n" + "#\n" + "expand_path() {\n" + - " \"$direnv\" expand_path \"$@\"\n" + + " local REPLY; __rp_absolute ${2+\"$2\"} ${1+\"$1\"}; echo \"$REPLY\"\n" + "}\n" + "\n" + + "# --- vendored from https://github.com/bashup/realpaths\n" + + "__rp_dirname() { REPLY=.; ! [[ $1 =~ /+[^/]+/*$ ]] || REPLY=\"${1%${BASH_REMATCH[0]}}\"; REPLY=${REPLY:-/}; }\n" + + "__rp_absolute() {\n" + + " REPLY=$PWD; local eg=extglob; ! shopt -q $eg || eg=; ${eg:+shopt -s $eg}\n" + + " while (($#)); do case $1 in\n" + + " //|//[^/]*) REPLY=//; set -- \"${1:2}\" \"${@:2}\" ;;\n" + + " /*) REPLY=/; set -- \"${1##+(/)}\" \"${@:2}\" ;;\n" + + " */*) set -- \"${1%%/*}\" \"${1##${1%%/*}+(/)}\" \"${@:2}\" ;;\n" + + " ''|.) shift ;;\n" + + " ..) __rp_dirname \"$REPLY\"; shift ;;\n" + + " *) REPLY=\"${REPLY%/}/$1\"; shift ;;\n" + + " esac; done; ${eg:+shopt -u $eg}\n" + + "}\n" + + "# ---\n" + + "\n" + "# Usage: dotenv [<dotenv>]\n" + "#\n" + "# Loads a \".env\" file into the current environment\n" + @@ -217,8 +233,8 @@ " rcfile=$(user_rel_path \"$rcpath\")\n" + " watch_file \"$rcpath\"\n" + "\n" + - " pushd \"$(pwd 2>/dev/null)\" >/dev/null\n" + - " pushd \"$(dirname \"$rcpath\")\" >/dev/null\n" + + " pushd \"$(pwd 2>/dev/null)\" >/dev/null || return 1\n" + + " pushd \"$(dirname \"$rcpath\")\" >/dev/null || return 1\n" + " if [[ -f ./$(basename \"$rcpath\") ]]; then\n" + " log_status \"loading $rcfile\"\n" + " # shellcheck disable=SC1090\n" + @@ -226,8 +242,8 @@ " else\n" + " log_status \"referenced $rcfile does not exist\"\n" + " fi\n" + - " popd >/dev/null\n" + - " popd >/dev/null\n" + + " popd >/dev/null || return 1\n" + + " popd >/dev/null || return 1\n" + "}\n" + "\n" + "# Usage: watch_file <filename> [<filename> ...]\n" + @@ -261,49 +277,52 @@ "# process - cause that process to run \"direnv dump\" and then wrap\n" + "# the results with direnv_load.\n" + "#\n" + + "# shellcheck disable=SC1090\n" + "direnv_load() {\n" + " # Backup watches in case of `nix-shell --pure`\n" + " local prev_watches=$DIRENV_WATCHES\n" + - " local prev_dump_file_path=${DIRENV_DUMP_FILE_PATH:-}\n" + - "\n" + - " # Create pipe\n" + - " DIRENV_DUMP_FILE_PATH=$(mktemp -u)\n" + - " export DIRENV_DUMP_FILE_PATH\n" + - " mkfifo \"$DIRENV_DUMP_FILE_PATH\"\n" + - "\n" + - " # Run program in the background\n" + - " (\"$@\")&\n" + - "\n" + - " # Apply the output of the dump\n" + - " local exports\n" + - " exports=$(\"$direnv\" apply_dump \"$DIRENV_DUMP_FILE_PATH\")\n" + - " local es=$?\n" + - "\n" + - " # Regroup\n" + - " rm \"$DIRENV_DUMP_FILE_PATH\"\n" + - " wait # wait on the child process to exit\n" + - " local es2=$?\n" + + " local temp_dir output_file script_file exit_code\n" + "\n" + - " if [[ $es -ne 0 ]]; then\n" + - " return $es\n" + - " fi\n" + + " # Prepare a temporary place for dumps and such.\n" + + " temp_dir=$(mktemp -dt direnv.XXXXXX) || {\n" + + " log_error \"Could not create temporary directory.\"\n" + + " return 1\n" + + " }\n" + + " output_file=\"$temp_dir/output\"\n" + + " script_file=\"$temp_dir/script\"\n" + "\n" + - " if [[ $es2 -ne 0 ]]; then\n" + - " return $es2\n" + - " fi\n" + + " # Chain the following commands explicitly so that we can capture the exit code\n" + + " # of the whole chain. Crucially this ensures that we don't return early (via\n" + + " # `set -e`, for example) and hence always remove the temporary directory.\n" + + " touch \"$output_file\" &&\n" + + " DIRENV_DUMP_FILE_PATH=\"$output_file\" \"$@\" &&\n" + + " { test -s \"$output_file\" || {\n" + + " log_error \"Environment not dumped; did you invoke 'direnv dump'?\"\n" + + " false\n" + + " }\n" + + " } &&\n" + + " \"$direnv\" apply_dump \"$output_file\" > \"$script_file\" &&\n" + + " source \"$script_file\" ||\n" + + " exit_code=$?\n" + "\n" + - " eval \"$exports\"\n" + + " # Scrub temporary directory\n" + + " rm -rf \"$temp_dir\"\n" + "\n" + " # Restore watches if the dump wiped them\n" + - " if [[ -z \"$DIRENV_WATCHES\" ]]; then\n" + + " if [[ -z \"${DIRENV_WATCHES:-}\" ]]; then\n" + " export DIRENV_WATCHES=$prev_watches\n" + " fi\n" + - " # Allow nesting\n" + - " if [[ -n \"$prev_dump_file_path\" ]]; then\n" + - " export DIRENV_DUMP_FILE_PATH=$prev_dump_file_path\n" + - " else\n" + - " unset DIRENV_DUMP_FILE_PATH\n" + - " fi\n" + + "\n" + + " # Exit accordingly\n" + + " return ${exit_code:-0}\n" + + "}\n" + + "\n" + + "# Usage: direnv_apply_dump <file>\n" + + "#\n" + + "# Loads the output of `direnv dump` that was stored in a file.\n" + + "direnv_apply_dump() {\n" + + " local path=$1\n" + + " eval \"$(\"$direnv\" apply_dump \"$path\")\"\n" + "}\n" + "\n" + "# Usage: PATH_add <path> [<path> ...]\n" + @@ -369,6 +388,63 @@ " export \"MANPATH=$dir:$old_paths\"\n" + "}\n" + "\n" + + "# Usage: PATH_rm <pattern> [<pattern> ...]\n" + + "# Removes directories that match any of the given shell patterns from\n" + + "# the PATH environment variable. Order of the remaining directories is\n" + + "# preserved in the resulting PATH.\n" + + "#\n" + + "# Bash pattern syntax:\n" + + "# https://www.gnu.org/software/bash/manual/html_node/Pattern-Matching.html\n" + + "#\n" + + "# Example:\n" + + "#\n" + + "# echo $PATH\n" + + "# # output: /dontremove/me:/remove/me:/usr/local/bin/:...\n" + + "# PATH_rm '/remove/*'\n" + + "# echo $PATH\n" + + "# # output: /dontremove/me:/usr/local/bin/:...\n" + + "#\n" + + "PATH_rm() {\n" + + " path_rm PATH \"$@\"\n" + + "}\n" + + "\n" + + "# Usage: path_rm <varname> <pattern> [<pattern> ...]\n" + + "#\n" + + "# Works like PATH_rm except that it's for an arbitrary <varname>.\n" + + "path_rm() {\n" + + " local path i discard var_name=\"$1\"\n" + + " # split existing paths into an array\n" + + " declare -a path_array\n" + + " IFS=: read -ra path_array <<<\"${!1}\"\n" + + " shift\n" + + "\n" + + " patterns=(\"$@\")\n" + + " results=()\n" + + "\n" + + " # iterate over path entries, discard entries that match any of the patterns\n" + + " for path in \"${path_array[@]}\"; do\n" + + " discard=false\n" + + " for pattern in \"${patterns[@]}\"; do\n" + + " if [[ \"$path\" == +($pattern) ]]; then\n" + + " discard=true\n" + + " break\n" + + " fi\n" + + " done\n" + + " if ! $discard; then\n" + + " results+=(\"$path\")\n" + + " fi\n" + + " done\n" + + "\n" + + " # join the result paths\n" + + " result=$(\n" + + " IFS=:\n" + + " echo \"${results[*]}\"\n" + + " )\n" + + "\n" + + " # and finally export back the result to the original variable\n" + + " export \"$var_name=$result\"\n" + + "}\n" + + "\n" + "# Usage: load_prefix <prefix_path>\n" + "#\n" + "# Expands some common path variables for the given <prefix_path> prefix. This is\n" + @@ -416,10 +492,11 @@ "\n" + "# Usage: layout go\n" + "#\n" + - "# Sets the GOPATH environment variable to the current directory.\n" + + "# Adds \"$(direnv_layout_dir)/go\" to the GOPATH environment variable.\n" + + "# And also adds \"$PWD/bin\" to the PATH environment variable.\n" + "#\n" + "layout_go() {\n" + - " path_add GOPATH \"$PWD\"\n" + + " path_add GOPATH \"$(direnv_layout_dir)/go\"\n" + " PATH_add bin\n" + "}\n" + "\n" + @@ -535,7 +612,7 @@ " conda=$(command -v conda)\n" + " fi\n" + " PATH_add \"$(dirname \"$conda\")\"\n" + - " env_loc=$(\"$conda\" env list | grep -- \"^$env_name\\s\")\n" + + " env_loc=$(\"$conda\" env list | grep -- '^'\"$env_name\"'\\s')\n" + " if [[ ! \"$env_loc\" == $env_name*$env_name ]]; then\n" + " if [[ -e environment.yml ]]; then\n" + " log_status \"creating conda environment\"\n" + @@ -809,7 +886,7 @@ "\n" + " __dump_at_exit() {\n" + " local ret=$?\n" + - " \"$direnv\" dump json 3\n" + + " \"$direnv\" dump json \"\" >&3\n" + " trap - EXIT\n" + " exit \"$ret\"\n" + " }\n" + diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/stdlib.sh new/direnv-2.21.3/stdlib.sh --- old/direnv-2.21.2/stdlib.sh 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/stdlib.sh 2020-05-08 15:58:17.000000000 +0200 @@ -10,6 +10,7 @@ # SC2059: Don't use variables in the printf format string. Use printf "..%s.." "$foo". shopt -s gnu_errfmt shopt -s nullglob +shopt -s extglob # NOTE: don't touch the RHS, it gets replaced at runtime @@ -19,7 +20,7 @@ DIRENV_LOG_FORMAT="${DIRENV_LOG_FORMAT-direnv: %s}" # Where direnv configuration should be stored -direnv_config_dir=${XDG_CONFIG_DIR:-$HOME/.config}/direnv +direnv_config_dir=${XDG_CONFIG_HOME:-$HOME/.config}/direnv # This variable can be used by programs to detect when they are running inside # of a .envrc evaluation context. It is ignored by the direnv diffing @@ -115,9 +116,24 @@ # # output: /usr/local/foo # expand_path() { - "$direnv" expand_path "$@" + local REPLY; __rp_absolute ${2+"$2"} ${1+"$1"}; echo "$REPLY" } +# --- vendored from https://github.com/bashup/realpaths +__rp_dirname() { REPLY=.; ! [[ $1 =~ /+[^/]+/*$ ]] || REPLY="${1%${BASH_REMATCH[0]}}"; REPLY=${REPLY:-/}; } +__rp_absolute() { + REPLY=$PWD; local eg=extglob; ! shopt -q $eg || eg=; ${eg:+shopt -s $eg} + while (($#)); do case $1 in + //|//[^/]*) REPLY=//; set -- "${1:2}" "${@:2}" ;; + /*) REPLY=/; set -- "${1##+(/)}" "${@:2}" ;; + */*) set -- "${1%%/*}" "${1##${1%%/*}+(/)}" "${@:2}" ;; + ''|.) shift ;; + ..) __rp_dirname "$REPLY"; shift ;; + *) REPLY="${REPLY%/}/$1"; shift ;; + esac; done; ${eg:+shopt -u $eg} +} +# --- + # Usage: dotenv [<dotenv>] # # Loads a ".env" file into the current environment @@ -214,8 +230,8 @@ rcfile=$(user_rel_path "$rcpath") watch_file "$rcpath" - pushd "$(pwd 2>/dev/null)" >/dev/null - pushd "$(dirname "$rcpath")" >/dev/null + pushd "$(pwd 2>/dev/null)" >/dev/null || return 1 + pushd "$(dirname "$rcpath")" >/dev/null || return 1 if [[ -f ./$(basename "$rcpath") ]]; then log_status "loading $rcfile" # shellcheck disable=SC1090 @@ -223,8 +239,8 @@ else log_status "referenced $rcfile does not exist" fi - popd >/dev/null - popd >/dev/null + popd >/dev/null || return 1 + popd >/dev/null || return 1 } # Usage: watch_file <filename> [<filename> ...] @@ -258,49 +274,52 @@ # process - cause that process to run "direnv dump" and then wrap # the results with direnv_load. # +# shellcheck disable=SC1090 direnv_load() { # Backup watches in case of `nix-shell --pure` local prev_watches=$DIRENV_WATCHES - local prev_dump_file_path=${DIRENV_DUMP_FILE_PATH:-} - - # Create pipe - DIRENV_DUMP_FILE_PATH=$(mktemp -u) - export DIRENV_DUMP_FILE_PATH - mkfifo "$DIRENV_DUMP_FILE_PATH" - - # Run program in the background - ("$@")& - - # Apply the output of the dump - local exports - exports=$("$direnv" apply_dump "$DIRENV_DUMP_FILE_PATH") - local es=$? - - # Regroup - rm "$DIRENV_DUMP_FILE_PATH" - wait # wait on the child process to exit - local es2=$? + local temp_dir output_file script_file exit_code - if [[ $es -ne 0 ]]; then - return $es - fi + # Prepare a temporary place for dumps and such. + temp_dir=$(mktemp -dt direnv.XXXXXX) || { + log_error "Could not create temporary directory." + return 1 + } + output_file="$temp_dir/output" + script_file="$temp_dir/script" - if [[ $es2 -ne 0 ]]; then - return $es2 - fi + # Chain the following commands explicitly so that we can capture the exit code + # of the whole chain. Crucially this ensures that we don't return early (via + # `set -e`, for example) and hence always remove the temporary directory. + touch "$output_file" && + DIRENV_DUMP_FILE_PATH="$output_file" "$@" && + { test -s "$output_file" || { + log_error "Environment not dumped; did you invoke 'direnv dump'?" + false + } + } && + "$direnv" apply_dump "$output_file" > "$script_file" && + source "$script_file" || + exit_code=$? - eval "$exports" + # Scrub temporary directory + rm -rf "$temp_dir" # Restore watches if the dump wiped them - if [[ -z "$DIRENV_WATCHES" ]]; then + if [[ -z "${DIRENV_WATCHES:-}" ]]; then export DIRENV_WATCHES=$prev_watches fi - # Allow nesting - if [[ -n "$prev_dump_file_path" ]]; then - export DIRENV_DUMP_FILE_PATH=$prev_dump_file_path - else - unset DIRENV_DUMP_FILE_PATH - fi + + # Exit accordingly + return ${exit_code:-0} +} + +# Usage: direnv_apply_dump <file> +# +# Loads the output of `direnv dump` that was stored in a file. +direnv_apply_dump() { + local path=$1 + eval "$("$direnv" apply_dump "$path")" } # Usage: PATH_add <path> [<path> ...] @@ -366,6 +385,63 @@ export "MANPATH=$dir:$old_paths" } +# Usage: PATH_rm <pattern> [<pattern> ...] +# Removes directories that match any of the given shell patterns from +# the PATH environment variable. Order of the remaining directories is +# preserved in the resulting PATH. +# +# Bash pattern syntax: +# https://www.gnu.org/software/bash/manual/html_node/Pattern-Matching.html +# +# Example: +# +# echo $PATH +# # output: /dontremove/me:/remove/me:/usr/local/bin/:... +# PATH_rm '/remove/*' +# echo $PATH +# # output: /dontremove/me:/usr/local/bin/:... +# +PATH_rm() { + path_rm PATH "$@" +} + +# Usage: path_rm <varname> <pattern> [<pattern> ...] +# +# Works like PATH_rm except that it's for an arbitrary <varname>. +path_rm() { + local path i discard var_name="$1" + # split existing paths into an array + declare -a path_array + IFS=: read -ra path_array <<<"${!1}" + shift + + patterns=("$@") + results=() + + # iterate over path entries, discard entries that match any of the patterns + for path in "${path_array[@]}"; do + discard=false + for pattern in "${patterns[@]}"; do + if [[ "$path" == +($pattern) ]]; then + discard=true + break + fi + done + if ! $discard; then + results+=("$path") + fi + done + + # join the result paths + result=$( + IFS=: + echo "${results[*]}" + ) + + # and finally export back the result to the original variable + export "$var_name=$result" +} + # Usage: load_prefix <prefix_path> # # Expands some common path variables for the given <prefix_path> prefix. This is @@ -413,10 +489,11 @@ # Usage: layout go # -# Sets the GOPATH environment variable to the current directory. +# Adds "$(direnv_layout_dir)/go" to the GOPATH environment variable. +# And also adds "$PWD/bin" to the PATH environment variable. # layout_go() { - path_add GOPATH "$PWD" + path_add GOPATH "$(direnv_layout_dir)/go" PATH_add bin } @@ -532,7 +609,7 @@ conda=$(command -v conda) fi PATH_add "$(dirname "$conda")" - env_loc=$("$conda" env list | grep -- "^$env_name\s") + env_loc=$("$conda" env list | grep -- '^'"$env_name"'\s') if [[ ! "$env_loc" == $env_name*$env_name ]]; then if [[ -e environment.yml ]]; then log_status "creating conda environment" @@ -806,7 +883,7 @@ __dump_at_exit() { local ret=$? - "$direnv" dump json 3 + "$direnv" dump json "" >&3 trap - EXIT exit "$ret" } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/direnv-test-common.sh new/direnv-2.21.3/test/direnv-test-common.sh --- old/direnv-2.21.2/test/direnv-test-common.sh 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/direnv-test-common.sh 2020-05-08 15:58:17.000000000 +0200 @@ -182,6 +182,11 @@ test_eq "${STATE}" "B" test_stop +test_start "utf-8" + direnv_eval + test_eq "${UTFSTUFF}" "♀♂" +test_stop + # Context: foo/bar is a symlink to ../baz. foo/ contains and .envrc file # BUG: foo/bar is resolved in the .envrc execution context and so can't find # the .envrc file. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/direnv-test.elv new/direnv-2.21.3/test/direnv-test.elv --- old/direnv-2.21.2/test/direnv-test.elv 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/direnv-test.elv 2020-05-08 15:58:17.000000000 +0200 @@ -22,10 +22,10 @@ try { m = (direnv export elvish | from-json) keys $m | each [k]{ - if (==s $k 'null') { - unset-env $k - } else { + if $m[$k] { set-env $k $m[$k] + } else { + unset-env $k } } } except e { @@ -129,6 +129,11 @@ test-eq $E:REMOVE_ME "" } +test-scenario "utf-8" { + direnv-eval + test-eq $E:UTFSTUFF "♀♂" +} + ## TODO: special-vars ## TODO: dump ## TODO: empty-var diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/direnv-test.fish new/direnv-2.21.3/test/direnv-test.fish --- old/direnv-2.21.2/test/direnv-test.fish 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/direnv-test.fish 2020-05-08 15:58:17.000000000 +0200 @@ -48,9 +48,15 @@ direnv_eval test_start dump - set -e LS_COLORS - direnv_eval - eq "$LS_COLORS" "*.ogg=38;5;45:*.wav=38;5;45" - eq "$LESSOPEN" "||/usr/bin/lesspipe.sh %s" - eq "$THREE_BACKSLASHES" "\\\\\\" + set -e LS_COLORS + direnv_eval + eq "$LS_COLORS" "*.ogg=38;5;45:*.wav=38;5;45" + eq "$LESSOPEN" "||/usr/bin/lesspipe.sh %s" + eq "$THREE_BACKSLASHES" "\\\\\\" test_stop + +# Currently broken +# test_start utf-8 +# direnv_eval +# eq "$UTFSTUFF" "♀♂" +# test_stop diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/direnv-test.tcsh new/direnv-2.21.3/test/direnv-test.tcsh --- old/direnv-2.21.2/test/direnv-test.tcsh 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/direnv-test.tcsh 2020-05-08 15:58:17.000000000 +0200 @@ -120,6 +120,14 @@ unsetenv FOO cd $TEST_DIR ; direnv_eval +# Currently broken +# cd $TEST_DIR/scenarios/"utf-8" +# direnv allow +# echo "Testing utf-8" +# direnv_eval +# test "$UTFSTUFF" -eq '♀♂' +# cd $TEST_DIR ; direnv_eval + # Context: foo/bar is a symlink to ../baz. foo/ contains and .envrc file # BUG: foo/bar is resolved in the .envrc execution context and so can't find # the .envrc file. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/scenarios/dump/.envrc new/direnv-2.21.3/test/scenarios/dump/.envrc --- old/direnv-2.21.2/test/scenarios/dump/.envrc 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/scenarios/dump/.envrc 2020-05-08 15:58:17.000000000 +0200 @@ -4,3 +4,7 @@ THREE_BACKSLASHES='\\\' \ bash -c "echo to stdout && echo to stderr >&2 && direnv dump" +log_status "direnv_load would previously hang if DIRENV_DUMP_FILE_PATH was not opened." +log_status "Expect the following to emit an error (which we suppress)." +log_status "As long as it doesn't hang, we're okay." +direnv_load true || true diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/scenarios/utf-8/.envrc new/direnv-2.21.3/test/scenarios/utf-8/.envrc --- old/direnv-2.21.2/test/scenarios/utf-8/.envrc 1970-01-01 01:00:00.000000000 +0100 +++ new/direnv-2.21.3/test/scenarios/utf-8/.envrc 2020-05-08 15:58:17.000000000 +0200 @@ -0,0 +1 @@ +export UTFSTUFF=♀♂ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/test/stdlib.bash new/direnv-2.21.3/test/stdlib.bash --- old/direnv-2.21.2/test/stdlib.bash 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/test/stdlib.bash 2020-05-08 15:58:17.000000000 +0200 @@ -20,16 +20,66 @@ fi } -# test find_up +test_name() { + echo "--- $*" +} + +test_name find_up ( load_stdlib path=$(find_up "README.md") assert_eq "$path" "$root/README.md" ) -# test source_up +test_name source_up ( load_stdlib cd scenarios/inherited source_up ) + +test_name direnv_apply_dump +( + tmpfile=$(mktemp) + cleanup() { rm "$tmpfile"; } + trap cleanup EXIT + + load_stdlib + FOO=bar direnv dump > "$tmpfile" + direnv_apply_dump "$tmpfile" + assert_eq "$FOO" bar +) + +test_name PATH_rm +( + load_stdlib + + export PATH=/usr/local/bin:/home/foo/bin:/usr/bin:/home/foo/.local/bin + PATH_rm '/home/foo/*' + + assert_eq "$PATH" /usr/local/bin:/usr/bin +) + +test_name path_rm +( + load_stdlib + + somevar=/usr/local/bin:/usr/bin:/home/foo/.local/bin + path_rm somevar '/home/foo/*' + + assert_eq "$somevar" /usr/local/bin:/usr/bin +) + +test_name expand_path +( + load_stdlib + tmpdir=$(mktemp -d) + trap 'rm -rf $tmpdir' EXIT + + cd "$tmpdir" + ret=$(expand_path ./bar) + + assert_eq "$ret" "$tmpdir/bar" +) + +echo OK diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/version.go new/direnv-2.21.3/version.go --- old/direnv-2.21.2/version.go 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/version.go 2020-05-08 15:58:17.000000000 +0200 @@ -1,3 +1,3 @@ package main -const Version = "2.21.2" +const Version = "2.21.3" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/direnv-2.21.2/version.txt new/direnv-2.21.3/version.txt --- old/direnv-2.21.2/version.txt 2020-01-28 20:48:16.000000000 +0100 +++ new/direnv-2.21.3/version.txt 2020-05-08 15:58:17.000000000 +0200 @@ -1 +1 @@ -2.21.2 +2.21.3