如何调试一个在启动时不运行的Launchd脚本?

39

我有一些来自Homebrew的Launchd脚本。 但是每次重启计算机时,我都必须手动运行它们:

launchctl load -w ~/Library/LaunchAgents/com.mysql.mysqld.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>KeepAlive</key>
  <true/>
  <key>Label</key>
  <string>com.mysql.mysqld</string>
  <key>Program</key>
  <string>/Users/dash/.local/Cellar/mysql/5.1.49/bin/mysqld_safe</string>
  <key>RunAtLoad</key>
  <true/>
  <key>UserName</key>
  <string>dash</string>
  <key>WorkingDirectory</key>
  <string>/Users/dash/.local/var</string>
</dict>
</plist>

我认为这应该在启动时发生。我错过了什么吗?


我认为这不会产生任何影响(因此我不将其作为答案),但是你可以尝试在测试时运行没有"-w"标志的命令(i.e. "launchctl load ~/Library/LaunchAgents/com.mysql.mysqld.plist"),然后重新启动。或者,也许尝试使用plist的完整文件路径(e.g. /Users/{you}/Library/LaunchAgents/com.mysql.mysqld.plist)。只是猜测而已。 - Alan W. Smith
1
不是真正的答案,但我相信LaunchControl会告诉你为什么。 - LCC
请查看我对类似问题的答案 - user711807
6个回答

47

我发现的最好的调试方式,在你的plist文件中:

<key>StandardErrorPath</key>
<string>/tmp/mycommand.err</string>
<key>StandardOutPath</key>
<string>/tmp/mycommand.out</string>

打开控制台应用程序,在“所有消息”中,您应该能够看到当您的应用程序失败或成功时的条目。就像这样:

4/28/15 10:43:19.938 AM com.apple.xpc.launchd[1]: (mycommand[18704]) Service exited with abnormal code: 1

我的问题在于ProgramArguments会将每个命令项作为数组中的项。 编辑: 在我的情况下,生成一个简单的外壳程序来包装shell脚本效果更好。 这个脚本设置了基本的文件夹结构,将shell脚本转换成OS X“应用程序”-https://gist.github.com/mathiasbynens/674099。这可能对你的mysql -u arg1命令更有效。

7

对我来说,目前为止其他的解决方案都没有帮助到我。我的问题有点难以调试,因为属性列表文件(plist文件)是正确的,脚本在终端中单独运行也很好。所有东西看起来都没问题,但是它却不起作用。

我通过执行以下命令来检查日志文件

tail -f /var/log/system.log

然后通过使用以下命令卸载并重新加载服务:

launchctl unload ~/Library/LaunchAgents/example.plist
launchctl load ~/Library/LaunchAgents/example.plist

我从日志文件中发现了一个错误消息:

Program specified by service is not a Mach-O executable file.

这到底意味着什么?我没有搜索。但是我感觉这是因为在shell脚本的开头没有添加#!/bin/bash。因为有时我懒得加这一行。

在添加了头之后,一切都正常了。


3

从OSX Yosemite 10.10开始,launchctl命令发生了变化。

以下命令将需要在重启时自动启动服务。

sudo launchctl bootstrap system /Library/LaunchDaemons/${YOUR_SERVICE_NAME}.plist
sudo launchctl enable system/${YOUR_SERVICE_NAME}
sudo launchctl kickstart -kp system/${YOUR_SERVICE_NAME}

注意:它将使用root用户启动服务并在整个系统范围内启动。
参考: Launchctl手册页面(https://ss64.com/osx/launchctl.html

2

启动命令需要作业标签作为参数,因此您可以使用以下命令启动它...

launchctl start com.myfile.hostname.plist

停止操作,只需按照以下步骤进行...
launchctl stop com.myfile.hostname.plist

在完成所有测试后,您需要注销然后重新登录以加载它,或者如果您的plist文件位于用户的Library文件夹中,请输入以下内容...

launchctl load ~/Library/LaunchAgents/com.myfile.hostname.plist

1
一个可能性:查看目录:
/private/var/db/launchd.db/

找到你的用户的 "com.apple.launchd.peruser.###" 文件。打开它并查看是否有以下条目:

<key>com.mysql.mysqld.plist</key>
<dict>
    <key>Disabled</key>
    <true/>
</dict>

如果是这样,请将其设置为<false/>。另一个需要查找相同内容的文件是:
/private/var/db/launchd.db/com.apple.launchd/overrides.plist

1
看起来很有希望,但遗憾的是它是<false/> - dd.
也许尝试完全剪掉它?我不知道那会有什么区别,但我只是试图寻找解决方法。 - Alan W. Smith

0

尝试重新命名它。 将文件名更改为:

~/Library/LaunchAgents/com.mysql.mysqld2.plist

将plist中的Label部分更改为:

<key>Label</key>
<string>com.mysql.mysqld2</string>

如果您保存了备份副本,请确保将其移动到~/Library/LaunchAgents/目录之外。
最后,不要使用launchctl来加载它,只需注销并重新登录即可。这将使launchd自己从您的“LaunchAgents”目录中获取它,并将一个变量(即launchctl)从混合中取出。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接