We have a scheduled job that we want to run on both our macOS and Linux hosts.

On Linux, with systemd we can just use this:


and the job will only execute if the first file exists, and the second file is absent (so we can pause the scheduled job from running, e.g. if we're testing a new version).

Is there an equivalent on macOS? I've seen others achieve a similar result by using Bash and just running `[[ -f /etc/this_file_must_exist ]] && run_my_job`` but this seems... not to be the ideal way.

launchd.plist's manpage (https://www.manpagez.com/man/5/launchd.plist/ -- official link seems down) has KeepAlive but that's for keeping the service up, not preventing it from starting.


1 Answer 1


Short answer: Nope.

launchd can start jobs at scheduled times (with the StartCalendarInterval key), when particular files are modified (WatchPaths), or when files appear in a particular directory (QueueDirectories), but it doesn't have a way to test existence of a specific file, nor to combine conditions the way you want to.

So... something like a bash wrapper is what you're looking at. You can either write a bash script and run that with a StartCalendarInterval trigger, or use the ProgramArguments array to embed a miniature script directly in the plist:

    <string>[[ -e /etc/this_file_must_exist ]] && [[ ! -e /etc/skip_if_this_exists ]] && exec /path/to/my_job</string>

Note: I'd recommend running your job from bash with exec; that makes the job replace the shell (rather than running as a subprocess), so launchd can monitor and manage it more directly.

  • That's good to know!
    – Seamus
    Commented Jun 23, 2020 at 2:12
  • Thanks! A bit unfortunate launchd is no longer open source, so we can't even easily suggest an enhancement supporting this.
    – michel-slm
    Commented Jun 26, 2020 at 0:06

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .