macos 在 fish 启动时添加到 $PATH 的相对路径

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/7064053/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-21 08:18:33  来源:igfitidea点击:

Add a relative path to $PATH on fish startup

macosshellenvironment-variablesfish

提问by Simon Perepelitsa

I want to add ./bin directory (which is relative to current shell directory) to $PATH on fish startup. Note that fishis a shell.

我想在鱼启动时将 ./bin 目录(相对于当前 shell 目录)添加到 $PATH 。请注意,这fish是一个外壳。

echo $PATH
set PATH ./bin $PATH
echo $PATH

If I place these lines inside ~/.config/fish/config.fishthe shell will echo the same collection of paths. Absolute paths are added properly.

如果我将这些行放在~/.config/fish/config.fishshell 中,将回显相同的路径集合。绝对路径已正确添加。

If I open the shell and type the same set PATH ./bin $PATHinside some directory containing binit is added successfully. However when there is no bininside current directory it shows me an error.

如果我打开 shell 并set PATH ./bin $PATH在包含bin它的某个目录中键入相同的内容,则会成功添加。但是,当bin当前目录中没有时,它会向我显示错误。

set: Could not add component ./bin to PATH.
set: Value too large to be stored in data type

I'm running fish 1.23.1 on OS X Lion.

我在 OS X Lion 上运行 fish 1.23.1。

采纳答案by Simon Perepelitsa

It seems like fishwon't add a non-existing directory path to PATH. That applies to relative paths too. But if you create bindirectory in your home directory set PATH ./bin $PATHwill work properly on each startup since it is executed from home. This is kind of a hack though.

似乎fish不会向 PATH 添加不存在的目录路径。这也适用于相对路径。但是,如果您bin在主目录中创建目录,set PATH ./bin $PATH则每次启动时都可以正常工作,因为它是从主目录执行的。不过,这有点像黑客。

回答by Dennis

The best way I have found to persistently add a path to your $PATHis

我发现持续添加路径$PATH的最佳方法是

set -U fish_user_paths $fish_user_paths ~/path/name

This prependsto $PATH. And since it's persistent, the path stays in $PATHon shell restarts.

这种预先考虑$PATH。而且由于它是持久的,所以路径在$PATHshell 重新启动时保持不变。

It's more efficient than putting a command in your config.fishto modify your $PATH, because it only runs once compared to running on every shell restart.

它比在您的 中添加命令config.fish来修改您的 更有效$PATH,因为与在每次 shell 重新启动时运行相比,它只运行一次。

The variable fish_user_pathsis intended to be set by the user1, as stated by ridiculousfish, the maintainer of fish.

该变量fish_user_paths旨在由用户1设置,如fish 的维护者fakefish所述。



Consider creating a fish function for convenience: 2

为方便起见,考虑创建一个fish函数:2

# ~/.config/fish/functions/add_to_path.fish
function add_to_path --description 'Persistently prepends paths to your PATH'
  set --universal fish_user_paths $fish_user_paths $argv
end

And use it as:

并将其用作:

$ add_to_path foo bar  # Adds foo/ and bar/ to your PATH


Notes

笔记

  1. On that page the author gives the example set -U fish_user_paths ~/bin. This overwrites fish_user_pathswith a single value of ~/bin. To avoid losing existing paths set in fish_user_paths, be sure to include $fish_user_pathsin addition to any new paths being added (as seen in my answer).

  2. My dotfiles contain a slightly more advanced version that skips adding duplicates https://github.com/dideler/dotfiles/blob/master/.config/fish/functions/add_to_user_path.fish

  1. 在该页面上,作者给出了示例set -U fish_user_paths ~/bin。这将fish_user_paths使用单个值覆盖~/bin。为避免丢失 中设置的现有路径fish_user_paths,请确保$fish_user_paths在添加任何新路径之外还包括(如我的回答所示)。

  2. 我的 dotfiles 包含一个稍微高级的版本,它跳过添加重复项https://github.com/dideler/dotfiles/blob/master/.config/fish/functions/add_to_user_path.fish

回答by Keith Thompson

I'd never heard of fishbefore this. I just installed it so I could try it out (and deleted a few paragraphs I had written here before realizing that fishis a shell).

fish在此之前我从未听说过。我刚刚安装了它,所以我可以尝试一下(并在意识到这fish是一个 shell之前删除了我在这里写的几段)。

It looks like set PATH dir-name $PATHis the right syntax to prepend a directory to $PATH.

看起来set PATH dir-name $PATH是将目录添加到$PATH.

But adding a relativedirectory name to $PATHis almost certainly a bad idea, and your shell is doing you a favor by warning you when the directory doesn't exist. (fishis designed to be user-friendly.)

但是,添加一个相对目录名$PATH几乎肯定是一个坏主意,当目录不存在时,您的 shell 通过警告您来帮您一个忙。(fish旨在方便用户。)

Use an absolute path instead:

改用绝对路径:

set PATH $PWD/bin $PATH

and first check whether $PWD/binexists, printing an error message if it doesn't.

并首先检查是否$PWD/bin存在,如果不存在则打印错误消息。

As for the "set: Value too large to be stored in data type" message, could you be adding the directory to your $PATHmultiple times? There should be some way to check whether a directory is already in $PATHbefore adding it.

至于“ set: Value too large to be stored in data type”消息,您是否可以$PATH多次将目录添加到您的目录中?$PATH在添加目录之前,应该有一些方法可以检查目录是否已经存在。

回答by dhardy

I think the answer is that using set -Uis a red herring. Instead, add the following to ~/.config/fish/config.fish:

我认为答案是使用set -U是一种红鲱鱼。相反,将以下内容添加到~/.config/fish/config.fish

if status --is-interactive
    set PATH $PATH ~/.local/bin;
end

回答by Florian D

direnv http://direnv.net/is a good utility to help with what you're doing.

direnv http://direnv.net/是一个很好的实用程序,可以帮助您完成正在做的事情。

Generally, prepending $PATH with ./bin is insecure, as anyone with write-access to a shared directory could hide malicious code in e.g. ./bin/ls. That code would execute when you run ls in the shared directory.

通常,在 $PATH 前面加上 ./bin 是不安全的,因为任何对共享目录具有写访问权限的人都可以将恶意代码隐藏在例如 ./bin/ls 中。当您在共享目录中运行 ls 时,该代码将执行。

direnv does not solve this problem (it works based on .envrc files, but anyone could be placing those), but at the very least it makes you aware when you cd into a directory that $PATH is getting modified:

direnv 并没有解决这个问题(它基于 .envrc 文件工作,但任何人都可以放置这些文件),但至少它让你知道当你 cd 进入一个 $PATH 正在被修改的目录时:

$ cd my_project
direnv: loading .envrc
direnv export: ~PATH