问题
I am setting up a simple Chef recipe to install a binary app. There is no package for it in Ubuntu or CentOS so I'm writing a recipe that does the following:
- Downloads the tar from source
- Extracts contents from tar
- Creates a bash script that adds the app_home to the global $PATH (it needs to be global)
- Reloads $PATH so the current logged in user can refer to it in the shell commands
I am good up to step 3, but I cannot get Chef to reload $PATH. I have tried placing the new export PATH=$PATH:/path/to/app/bin in both .bash_profile
as well as /etc/profile.d/
with no success.
If I exit the shell and re-ssh I see the PATH correctly, but never in the same session as when I ran sudo chef-client
.
Is there any way that Chef can touch
or reload the PATH automatically so that the current logged in user can make use of it?
回答1:
Short answer: No. Environment variables are inherited from the parent. A child process cannot change its parent's environment variables.
Long answer: When leveraging signals (or other forms of IPC), you could signal the parent to reload environment variables from a file.
If you have a file ~/my_environment
containing the following:
export FOO="bar"
Execute the following code in your bash:
function reload_environment { source ~/my_environment; }
trap reload_environment SIGHUP
reload_environment
Run echo $FOO
and see it outputs bar
Now, when another processes sends a HUP signal to this bash process, it'll reload the environment variables in ~/my_environment
by running the reload_environment
function.
Lets give it a try. Check what's the bash's PID by running
echo $$
Next, change the content of ~/my_environment
to:
export FOO="fish"
Then, send a SIGHUP to the bash's PID:
kill -HUP 12133
If everything went well, running echo $FOO
on that bash session would yield fish
For your case, you can use inotify to send the HUP signal to bash when ~/my_environment
changes. If you're running chef-client
from bash, you could send a HUP signal to your parent PID.
回答2:
why not just do:
ENV['PATH']="#{ENV['PATH']}:/path/to/app/bin"
In your chef cookbook? If you've already got the additional path in there you'll wind up with it in the PATH twice, but that won't hurt anything (you can even made the assignment conditional on the additional path not being already present by adding unless ENV['PATH'].split(/:/).include?("/path/to/app/bin")
to avoid that).
NOTE: this answer doesn't answer the original question, which isn't possible to solve.
来源:https://stackoverflow.com/questions/22021741/how-to-have-chef-reload-global-path