在存储在主文件夹中的登录名上运行bash脚本?


19

当我尝试从中加载LaunchAgent plist时,launchctl找不到在主目录中运行脚本的方法。

我的代码是:

<?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>ProgramArguments</key>
    <array>
        <string>bash</string>
        <string>~/script.sh</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>Label</key>
    <string>com.tyilo.test</string>
</dict>
</plist>

我已经尝试过使用bash和不使用bash,也都用替换~$HOME。我也尝试过使用bash -c它而不工作。

错误代码为:

`com.tyilo.test: bash: ~/script.sh: No such file or directory`

尝试放置完整路径,例如/Users/name/script.sh(也可以使脚本可执行,并使用第一行#!/ bin / bash并直接运行它)
user151019 2012年

我无法使用完整路径,因为它要在多个帐户和计算机上使用。
蒂洛2012年

1
如果要在我的多个帐户中使用它,则应将其放在/ usr / local / bin /中,而不是在每个用户的$ HOME中复制它的多个副本。了解该脚本要完成的工作会很有帮助。这听起来像是IMO的LoginHook的工作。
TJ Luoma 2012年

Answers:


14

EnableGlobbing启用波浪号和通配符扩展ProgramArguments

<key>EnableGlobbing</key>
<true/>
<key>ProgramArguments</key>
<array>
    <string>say</string>
    <string>~/*</string>
</array>

它不会影响ProgramWatchPaths,但是WatchPaths默认情况下,波浪线扩展会起作用。


这是更好的方法。在哪里可以查看LaunchAgent plist中的密钥文档?
蒂洛2013年

男子launchd.plist。或查看此博客文章我的网站
Lri

1
这也对我有帮助。在以下Mac OS X版本中尝试过:10.7、10.8和10.9。
Dj S

6
请注意:优胜美地(Mac OS X 10.10+)中已删除此功能。
亚历克斯·格雷

看起来也不是在10.9.5中
ocodo

18

EnableGlobbing在OS X Yosemite 10.10上不起作用。它已被弃用( ref)。

您可以在日志中查看The EnableGlobbing key is no longer respected. Please remove it.(来自/var/log/system.log

问题是launchdcwd(当前工作目录)是/,所以您不能./像某些人所说的那样使用。

要在家中运行脚本,简单的方法是使用(bash|zsh|sh) -c。选项。这样,您将可以使用代字号~$HOME变量。

<?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>org.your.stuff</string>
    <key>ProgramArguments</key>
    <array>
      <!-- here is the important thing -->
      <string>zsh</string>
      <string>-c</string>
      <string>~/you/script/in/your/home</string>
    </array>

    <!-- code below is just for the example -->
    <!-- Keep running... -->
    <key>KeepAlive</key>
    <true />
    <!-- ...every day. In sec, 60*60*24 = every day -->
    <key>ThrottleInterval</key>
    <integer>86400</integer>
  </dict>
</plist>

2
我不认为你可以使用带波浪号sh; 当Bash作为涉及时sh,它将以POSIX兼容模式运行,该模式将禁用许多Bash扩展。
三胞胎2015年

~/正在吞噬,因此不受支持。./只要守护程序保存在用户主库中,就可以使用。(~/Library/LaunchAgents
布鲁诺

9

我发现执行此操作最可靠的方法是使用shHOME环境变量:

<?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>ProgramArguments</key>
    <array>
        <string>sh</string>
        <string>-c</string>
        <string>"$HOME/script.sh"</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>Label</key>
    <string>com.tyilo.test</string>
</dict>
</plist>

注意:引号是必需的。


2

知道为什么需要从用户的主目录运行脚本会很有帮助。如果您需要脚本的用户简称,则可以通过将其分配给变量来获取它

user=`whoami`

然后$user在脚本中使用。

我真的会将脚本放在主目录之外的其他位置,然后同一台计算机上的其他用户可以访问该脚本。您可以使用共享目录或将脚本放入/ Library / Scripts /

您将必须使用完整路径启动plist。另外,在启动的plist中,您不需要指定<string>bash</string>脚本,因为它应该包含shebang并且应该是可执行的。


将其指定bash为要执行的实际命令是一个很好的后备,并且没有任何实际的损害。如果他没有shebang,或者忘记使脚本可执行(o = rwx),则bash仍将调用/执行脚本。
杰森·萨拉兹

1
用户名应该已经有一个变量,例如$ USER或$ LOGNAME。另外,共享Unix脚本的通常位置是/ usr / local / bin /(不是您不能将它们放在其他位置,但是/ usr / local / bin /很可能已经在$ PATH中)。
TJ罗马

使用whoami只是获得与$ USER或$ LOGNAME相同信息的另一种方法。我建议上面的位置,因为我不想假设任何发问者。另外,在尝试使启动的plist工作之前,该脚本实际上需要能够从CLI运行。
afragen 2012年

1

它可执行吗?

chmod 700 ~/script.sh

在终端。另外,我不会使用$ HOME或〜,而是使用文件的实际路径。

<?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>com.tyilo.test</string>
    <key>ProgramArguments</key>
    <array>
        <string>/path/to/script.sh</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
</dict>
</plist>

投票否决的原因是什么?
TJ Luoma 2013年

1

如果脚本是用户代理(因此位于主文件夹的库中),则launchd当前工作目录为主文件夹。UNIX指的是主目录,路径中带有句点。

因此,基本上,使用./script.sh代替~/script.sh。;-)


3
不,启动的工作目录实际上是/,而不是'〜'。
蒂洛2013年

@Tyilo我不确定你的意思。如果您的意思是“在所有情况下,即使在用户模式下,launchd的工作目录都是根目录”,请提供参考。如果您的意思是“ launchd使用斜杠而不是波浪号”,请再次阅读我的文章。顺便说一句,我在启动中安排了几个脚本,它们遵循了我描述的行为。;-)
Constantino Tsarouhas 2013年

1
@RandyMarch我在东京展开剂~/Library/LaunchAgents的论据:sh-cecho $HOME > /Users/Tyilo/launchd_home.txt。运行时/Users/Tyilo/launchd_home.txt包含的文件/不是/Users/Tyilo
蒂洛2013年
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.