如何使用 GUI 在 MacOS 上设置环境变量?

如何使用 GUI 在 MacOS 上设置环境变量?

我正在尝试向几个人提供有关如何在 MacOS 中设置环境变量的说明。

我希望变量是永久的,不需要重新启动,并且它必须适用于所有 GUI 应用程序。

不幸的是,任何需要 vim 甚至 nano 的解决方案都行不通。

如何仅使用 GUI 应用程序即可完成此操作?(越简单越好)

答案1

我已经建立了一种方法来做到这一点,使用文档文本文件。但是,如果用户想要决定设置哪些环境变量,则需要使用 nano。如果您提供该功能,则用户不必使用 nano。但是,该过程很棘手,安装时有很多陷阱,因此即使这样,对您的用户来说可能也太多了。但我想让任何想要它的人都可以使用它。由于我无法在此处附加文件,我想我会将所有文件内容放入下面的代码块中。使用的方法是创建 MacOS 在启动时加载的 .plist 文件,该文件包含 bash 代码,可读取用户主目录中提供的包含要设置的环境变量的文本文件。

以下是 environment.plist 文件的内容:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>Label</key>
    <string>my.startup</string>
    <key>ProgramArguments</key>
    <array>
        <string>/bin/bash</string>
        <string>-c</string>
        <string>while read LINE; do NAME=${LINE%%=*}; VALUE=${LINE#*=}; eval launchctl setenv $NAME &quot;$VALUE&quot;; done &lt;~/environment.txt; echo &quot;environment.plist ran on $(date)&quot; &gt;&gt; ~/environment.plist.log</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
</dict>
</plist>

这是一个示例 environment.txt 文件,它将被放置在用户的主目录中,用于设置一些环境变量:

LOCAL_ROOT=/Users/$USER/archive
SOFTWARE_ROOT=$LOCAL_ROOT/PKGS
REPO_DIR=$SOFTWARE_ROOT/repositories
RSOURCEPATH=$REPO_DIR/rscripts/libraries

这是我的 environment.readme.txt 文件,与用户主目录中的 environment.txt 配套:

This file accompanies file environment.txt.

PLACE GLOBAL ENVIRONMENT VARIABLES IN ~/environment.txt   !!!!

Full instructions describing environment.txt can be found in the file:
    environment.plist.readme.txt
which should be in the directory ~/Library/LaunchAgents

Edit environment.txt to set the environment variables that you want.  You can
edit the file with any text editor, e.g. nano:
    nano ~/environment.txt
In nano, use the arrow keys to move around, the backspace key to delete text,
and use control/x followed by a Y and enter to exit and save the changes. Also,
follow the steps in environment.plist.readme.txt to check the file for correct
line endings and fix them if necessary.

PLACE GLOBAL ENVIRONMENT VARIABLES IN ~/environment.txt   !!!!
THEY CAN USE OTHER PRE-EXISTING ENVIRONMENT VARIABLE VALUES IN THEM !!!!
FOR EXAMPLE: XXX=/Users/$USER/xxx

LOG OUT AND LOG BACK IN FOR THE CHANGES TO TAKE EFFECT!

最后,这里是 environment.plist.readme.txt 文件,其中包含详细的使用说明:

PLACE GLOBAL ENVIRONMENT VARIABLES IN ~/environment.txt   !!!!

This accompanies file environment.plist (for Mac computers running MacOS) that
sets global environment variables so that they can be seen by apps started via a
mouse click on an icon.  (Environment variables set in a shell profile file
cannot be seen by apps started that way).

The environment.plist file should load and run automatically whenever you boot
your Mac.

To use the environment.plist file, while logged in as your username and not as
root user, copy this file and environment.plist to your directory named:
    ~/Library/LaunchAgents
Then set the correct file permissions with:
    chmod u+rw,g+r,o+r ~/Library/LaunchAgents/environment.plist
Also, make sure the file hasn't been quarantined by an anti-virus program or
had extended attributes attached to it that might interfere with its loading,
by using the command:
    ls -l
You should see permissions for the file as -rw-r--r-- and if an @ occurs after
this, it means the file has extended attributes, which you can view with:
    xattr ~/Library/LaunchAgents/environment.plist
The attribute com.apple.quarantine will definitely prevent the file from loading
and other attributes might also block it.  You can remove an attribute with:
    xattr -d <attribute name> ~/Library/LaunchAgents/environment.plist
Then test the .plist file for correctness with the command:
    plutil ~/Library/LaunchAgents/environment.plist

Next, copy environment.txt and environment.readme.txt to your ~ (home) directory
and edit environment.txt to set the global environment variables you desire.
(The sample environment.txt file has some sample settings). You can use existing
environment variables such as USER as part of your environment variable
definitions in environment.txt, e.g. "XXX=/Users/$USER/xxx", and you can use
your new environment variables in subsequent environment variable definitions in
the file.

For the next step, you need to know your user id uid number, which you can find
with this command:
    id
Typically on a Mac the uid often is 501.  Using the uid, test the .plist and
.txt files with these commands:
    launchctl bootout gui/501 ~/Library/LaunchAgents/environment.plist
    launchctl enable user/501/~/Library/LaunchAgents/environment.plist
    launchctl bootstrap gui/501 ~/Library/LaunchAgents/environment.plist

Each time environment.plist runs, it writes a line at the end of a log file
showing the date it ran.  Examine that file to see if it has a new entry, using
this command:
    cat ~/environment.plist.log
Each time you log in, and each time you run the three launchctl commands above,
a new line should be added to the log file, so you should see one line in the
file after running the above launchctl commands.

At this point, logging out and back in should cause the environment.plist file
to run and read the environment.txt file and assign those environment variables.
You should see them in any program you start yourself, but they won't show up in
any program started by MacOS automatically at login (and I don't know how to fix
that problem).

If everything works well, skip the remainder of this document, but if not, read
on and you might be able to fix the problem.

It is important that the environment.txt file have only a newline (\n) as line
end, not \r\n or only \r. If you created it with the nano editor, it should be
okay. To find out what the line endings are, you can use this command:
    hexdump ~/environment.txt | less
Look through the hex bytes to find 0a (\n), 0d (\r), or 0d followed by 0a. It
should occur at the end of each line (each hex byte XX corresponds to one
character in the file) and particularly after the last line. Use the space bar
to scroll through the bytes and q to quit out of the 'less' program. If you find
only a 0d and no 0a, fix the file like this:
    tr '\r' '\n' ~/environment.txt >env.txt
    mv env.txt environment.txt
If you find 0d followed by 0a, fix the file like this:
    tr -d '\r' ~/environment.txt >env.txt
    mv env.txt environment.txt

If the log file ~/environment.plist.log doesn't exist or doesn't have a new line
at the end of the file showing the date you ran the launchctl commands above,
then something is wrong, which is frequently the case. You need to go back and
check all the above steps and recheck the file contents, owner, and permissions
carefully and try the launchctl commands a second time.  If it still isn't
adding a new entry to the log file when you run those commands, then restarting
your computer might fix the problem.  Do that and try again.  Otherwise, I don't
know what else to try.

If the log file looks okay, test to see if your environment variables have been
set by exiting the Terminal application completely, then restarting it, and
using this command:
    echo $<ENVIRONMENT VARIABLE NAME>
Use the name of one of your environment variables, e.g. 'echo $LOCAL_ROOT'
You should see the VALUE you assigned to that environment variable printed out.
The value will be empty if you have not exited and restarted your terminal
console app after running the launchctl commands.

Next, log out and log back in to your computer and go into the Terminal app and
do the above 'echo' command again. If it doesn't print out the expected
environment variable value, this is probably because Terminal was started by
MacOS automatically when you logged in.  Programs that start automatically will
not have access to the environment variables.  Only programs that you start
yourself will have access.  Try exiting the terminal app and restarting it, then
check the environment variable again.  If it still isn't okay, run through
everything one more time to see if you can get it working, and if not, I don't
have any other ideas to recommend.

Finally, once you see that the 'echo' command shows an environment variable
value, double-check that the variable is accessible from an app started with a
mouse-clicked-icon. If you have RStudio or R installed, start that app with the
mouse. Then, at the console prompt, type the command:
    Sys.getenv("<ENVIRONMENT VARIABLE NAME>")
It should show the value of the environment variable with that name.  E.g.:
    Sys.getenv("LOCAL_ROOT")

CAUTION: If you allow MacOS to restore your apps and windows when you log in, or
if you specify certain apps to be started automatically at login using System
Preferences, Users and Groups, Login Items, those automatically started apps
will not see the new environment variables.  The solution is to close and
re-open any app that was started automatically at login and needs to use those
environment variables.

Theory of operation: When a user logs in, MacOS locates .plist files in folder
~/Library/LaunchAgents and parses them and executes commands in them. The
accompanying plist file, environment.plist, has commands to run a bash shell
subcommand that reads file ~/environment.txt and parses it as a series of
NAME=VALUE lines, then calls 'launchctl setenv' to set NAME as a global
environment variable with value VALUE, and finally, it writes the date to the
end of the log file. All that is accomplished with one long BASH command in the
.plist file, shown here broken into five lines but present in a single LONG line
in the .plist file:
    while read LINE; do NAME=${LINE%%=*}; VALUE=${LINE#*=};
    eval launchctl setenv $NAME &quot;$VALUE&quot;;
    eval export $NAME=&quot;$VALUE&quot;;
    done &lt;~/environment.txt;
    echo &quot;environment.plist ran on $(date)&quot; &gt;&gt; ~/environment.plist.log

Note that semicolons separate BASH commands on one line, &quot; is translated
into the character " (quote), and &lt; is translated into the character < (less
than), and &gt; is translated into the character > (greater than) by the .plist
parser.  The .plist file must have permissions u+rw,g+r,o+r and be owned by the
home directory user and not have a quarantine extended attribute in order for it
to be loaded by MacOS automatically when you log in.

相关内容