Why Does Apple Use launchd?

Here's a crontab entry to run "echo 'Hello World'" every five minutes:

0-59/5    *    *    *     *   echo Hello World

Here's the .plist (property list) file you should create in OS X to do the same thing:

<?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.veure.test</string>
    <key>ProgramArguments</key>
    <array>
        <string>echo</string>
        <string>Hello, World</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>StartInterval</key>
    <integer>300</integer>
</dict>
</plist>

Apple lists there reasons why this is a good thing, but I confess that it seems more trouble than it's worth.

9 Comments

I despise both formats.

How many languages have a reliable parser / emitter for cron's syntax? How about XML?

I don't use Mac OS X and I've only had to deal with launchd once but I was very impressed by it. It's not just a replacement for the odd cron job but for everything we use inet.d / cron for on other Unix systems.

It makes things trivial on OSX that are hard on other systems. If I'm not root and I want to start my own daemon on Linux I'm going to have to do something like write a cronjob that periodically check up on my daemon and restarts it if it's down.

On OSX you just craft a simple XML file, load it into launchd and it'll take care of it for you henceforth. Including automatically logging for you and restarting if the program goes down or if you've rebooted.

Machine readable config files across the board also give you a lot of advantages. If I upgrade my Debian system and it spots that I've changed something in /etc it can only give me a unified diff of my file against the system one and ask me what I want.

If both files were a plist it would be trivial to ask more direct questions like "I see you've added the key frob=blob to the default config. Would you like me to use the distribution's new file and merge your changes into it?".

On Debian the only way you could do that is to create reliable parsers for every single file format that lives in /etc, good luck with that.

As an aside I recently upgraded to Ubuntu 10.04 and they've replaced init.d with Upstart. I was hoping it would be something like launchd but it looks like it doesn't give me cron features, doesn't allow unprivileged users to interface with it, and it has its very own custom configuration format which I can't easily emit from anywhere else.

...you just craft a simple XML file...

...You keep using that word. I do not think it means what you think it means.

This is kinda tangential, but I thought well-crafted XML documents were supposed to be all "semantic" and stuff.

That plist seems to depend on elements following each other rather than being nested inside each other. There is no inferrable relationship; you just have to KNOW how it's supposed to look.

At this point, in my mind, you're just using the formatting of SGML languages to create an extremely verbose (yet still brittle) key/value mapping. All the pain of XML with none of the benefit. Kinda surprised something like this would come out of Apple.

Here's how you start a simple program on Debian at boot, and here's the Upstart version. Here's OSX before launchd and OSX after launchd.

Which one do you think is the simplest?

ok, even if I can understand the needs for dict/string/integer labels, but why do we need a key label? Can we just say something like "<RunAtLoad>true</RunAtLoad>"

What I want to know is why on Earth Apple abandoned the old NeXTStep JSON-like plist format in favour of XML. The old format was just as well-documented as XML (hah!), and a good deal easier for both humans and machines to read.

axqd.net: Because XML works better if you restrict your element namespace. Doing it like this means they can have a simple DTD. It's also easier to set up a key hook where you know the input is going to be a string than setting up a listener for arbitrary tags in a lot of XML parsers.

Ben Morrow: I have no idea, but presumably because as the Wikipedia article points out the old format couldn't represent all the NSValue types whereas the new format can.

The old format wasn't easier for humans or machines. When I wrote files in the NeXTSTEP format I had to look at the manual to make sure I was getting the syntax right, with XML I (and my editor) already knew how.

The same goes for machines. Language $foo already has an XML parser/emitter. It probably doesn't have the same support for NeXTSTEP property lists.

In any case. Bikeshedding the specifics of the format misses the point. It doesn't matter that it's ugly as long as it's uniformly ugly. Uniformity means you only have to solve the problem of reading configuration files once.

Well, xml sucks for configuration - unless you use a gui. It's sad people use it where it doesn't fit. Policykit is a good example.

Leave a comment

About Ovid

user-pic Have Perl; Will Travel. Freelance Perl/Testing/Agile consultant. Photo by http://www.circle23.com/. Warning: that site is not safe for work. The photographer is a good friend of mine, though, and it's appropriate to credit his work.