The immediate problem is that your .plist file isn't correctly formatted -- the contents of <string>...</string>
should be encoded with HTML entities, i.e. &
needs to be encoded as &
(note: you can check the format of .plist files with plutil -lint filename.plist
). But there are some other changes that need to be made...
Starting programs with launchd is rather different than starting them from a shell. The biggest difference is that from the shell, you want the program to go into the background and run independently of the shell, so you wrap it in nohup ... &
. With launchd, it's actually best for the program to stay in the "foreground" so launchd can keep an eye on it.
Also, the elements of ProgramArguments won't get parsed by a shell, so listing the command and its arguments with spaces between them doesn't work -- make each argument a separate element of the array.
Here's my stab at a synergy .plist. I haven't tested this, so it may need a little tweaking to work properly (see notes below):
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC -//Apple Computer//DTD PLIST 1.0//EN http://www.apple.com/DTDs/PropertyList-1.0.dtd >
<plist version="1.0">
<dict>
<key>Label</key>
<string>local.synergy</string>
<key>ProgramArguments</key>
<array>
<string>/usr/bin/synergys</string>
<string>-f</string>
<string>--config</string>
<string>/Users/USER/bin/conf/synergy.conf</string>
</array>
<key>RunAtLoad</key>
<true/>
<key>Nice</key>
<integer>10</integer>
<key>KeepAlive</key>
<false/>
<key>AbandonProcessGroup</key>
<true/>
</dict>
</plist>
The last two keys above deal with how launchd should react if/when the synergys program exits. By default, it kills any surviving subprocesses and launches a new instance; these two keys supress both parts, which may or may not be what you want. Also, one thing this doesn't do that your version with nohup
does is redirect stdin and stdout to nohup.out (in case the terminal goes away); instead IIRC launchd logs things that get sent to them. If synergys is in the habbit of sending output, you might want to add something like this to the .plist:
<key>StandardOutPath</key>
<string>/dev/null</string>
<key>StandardErrorPath</key>
<string>/dev/null</string>
Also, as mankoff said, you should put this in ~/Library/LaunchAgents so it'll be autoloaded every time you log in. Oh, and you should probably add a local.
prefix to the filename (as I did with the label) to conform to the reverse-DNS naming convention.
Okay, I found a solution...
Chris Johnsen has a good writeup of what causes this problem on github.
His tools work, but a better solution, if you have homebrew installed to:
brew install reattach-to-user-namespace
Then in your ~/.tmux.conf
add these lines:
set-option -g default-command "reattach-to-user-namespace -l zsh" # or bash
bind C-c run "tmux show-buffer | reattach-to-user-namespace pbcopy"
bind C-v run "reattach-to-user-namespace pbpaste | tmux load-buffer - && tmux paste-buffer"
The first line ensures your shell can talk to pbpaste
, pbcopy
and launchctl
now with no worries.
The second line lets you copy the tmux
paste buffer into the Mac's paste buffer by typing control-b control-c (replace control-b with your tmux prefix key).
The third line will directly paste the Mac's paste buffer by typing control-v. As a side-effect it copies the Mac's paste buffer into tmux
's paste buffer.
I'd prefer if I could nuke tmux
's paste buffer entirely and have it paste directly into the Mac`s paste buffer, but... oh well.
Best Answer
The trouble goes away if I uncomment the
-F
switch (which I commented while I was trying to get some other part of the set up to work). The-F
switch runs Dovecot in the foreground and does not daemonize.From this answer on SuperUser:
In this case it didn't kill the program (as I wouldn't expected if the switch was the wrong one), it just relinquished control so it wouldn't/couldn't shut it down.
Note to self, try the obvious thing, your assumptions may be wrong.