So, I spent first five months of this year on a grueling, panic-driven-development project on Mac OS X. As my longest single Mac engagement, I’m afraid this can’t help but wear down my enthusiasm for the platform.

It doesn’t help that what I was working on was well into the edge-case realm: our stuff needed to silently update itself in the background, which gets into the management of daemons, starting and stopping them at will. This isn’t bad in theory, but getting it to work consistently across 10.4 through 10.6 is grueling. An always-on daemon sets a RunAtLoad property in its /Library/LaunchDaemons plist in order to come up immediately and stay up. Uninstalling and/or replacing such a daemon is tricky, as launchd keeps track of what daemons it has loaded and thinks are still running. The worst thing to do is to just kill the process… instead, you need to use launchctl to load or unload the daemon as needed. And, as a root-owned process, you need to perform this launchctl as root. Oh, and you’d better not delete the plist before you unload the daemon, since launchctl takes the path to the plist, so doing things in the wrong order can leave you with rogue daemons you can’t unload. And if you don’t unload the old daemon, a new launchctl load does nothing, as launchd thinks the original daemon is still running.

Now throw in some user agents. These are like daemons, except that they run for each user at login, and are owned by the user. So to uninstall or update, you need to launchctl unload as each user. Which is possible with sudo -u username in a shell script, unless you’re on 10.4 and you get the user list from /usr/bin/users, as the 10.4 version truncates user names to 8 characters, breaking the sudo.

Oh, and who’s doing these unloads? A script in an .mpkg installer. Which is a whole ‘nother bundle of fun, given how fabulously broken is Package Maker, Apple’s utility for creating .pkg and .mpkg installers. Package Maker crashes frequently, doesn’t consistently persist (especially when source-controlled) settings for file ownership, and creates broken installers when invoked by the command-line utility /usr/bin/packagemaker, making it utterly unsuitable for use in Makefiles or other automated build processes. IMHO, Package Maker is as big an ass-muffin as I’ve ever seen come out of Cupertino, at least since that quickly-pulled iTunes 2 release that reformatted the host drive.

Working with all these taped-together technologies — desperately trying shell script voodoo in an .mpkg post-install step to make things right — eventually wore me out. And granted, this is an edge case: most Mac apps can be distributed as app bundles without installers, and most installers can require the user to restart if it’s making radical changes like installing or updating daemons (not an option for me because the installer runs in the background, called by another daemon). Still, it’s enough to make you long for the “curated”, locked-down walled garden of the App Store, whose distribution and update system really does work remarkably well.

With the Mac all but expelled from this week’s WWDC, some pundits are happy to declare the death of the Mac. That’s a silly overstatement, but it is sensible to accept that after a decade of improvement and marketing, the Mac is a mature platform, likely secure at its 10%-or-so market share. What else would we want Apple to do with the Mac? I’d like to see things fixed and cleaned up, dubious legacies cleared out and things set right. And Apple has done that. Problem is, the result is not Mac OS X 10.7, it’s iOS 4.

But then again, if the iPad replaces the laptop for some number of users, this is a brilliant way to grow Apple’s share — nibbling away at traditional computers cannibalizes the Mac somewhat, but chows away mostly at Windows.

Suffice to say I’m very happy to be re-orienting myself to iPhone/iPad/iPod-touch development. It’s got the feel of a somewhat clean start, based on proven technology, but not burdened by old breakage. Now I’ve got some catching up to do to adapt to all the changes in iOS 4.

Leave a comment

You must be logged in to post a comment.