After upgrading to Mojave, my rsync based backup script run via a launch agent in ~/Library/LaunchAgents, could no longer read some directories in ~/Library.
How to run a LaunchAgent that runs a script which causes failures because of System Integrity Protection
launchdsip
Best Answer
I've spent a few weeks trying to sort this out. I agree that the currently accepted answer is not really a solution -- it's not much better than just disabling SIP altogether.
My solution is a totally hacky workaround, but doesn't require whitelisting
bash
entirely. Update: Slightly less hacky workaround below.Update 20190226: As detailed in the Restic issue linked below, this seems to have stopped working. The original binaries I created with this method continue to work without errors for some strange reason, but I can't give access to new binaries directly using this method.
Overview
open /path/to/MyApp.app
but not by directly using the executable stored in e.g.MyApp.app/Contents/Resources/
)For Step 1, you can easily package your script as an app by using tools built into MacOS such as Automator.app or Script Editor, or Platypus also works.
Example contents of such an app might be a simple AppleScript (in Script Editor) such as:
From Script Editor, use the dropdown in the save menu to save as an application, then CLOSE SCRIPT EDITOR.
Add this app to Full Disk Access through
System Preferences
->Security & Privacy
.NB: If you didn't save and close Script Editor prior to adding to FDA as instructed, it seems that some kind of invisible process (automated background saves?) will change something (some kind of timestamp or hash?) that is required for Full Disk Access, which can some intermittent errors that were a major headache to figure out. So if you didn't do this, remove your app from FDA, save and close Script Editor, then add back to FDA.
For your LaunchAgent, use something like:
Root access
If your backup script needs root access (e.g. to back up root-owned 0600 files), you're in for another set of hacky workarounds, since
/usr/bin/open
won't seem to run anything as root (even if you specify theUserName
key in in a root-owned/Library/LaunchDaemons/
plist. (I'd be happy to open this as a separate question if appropriate, since I think the below workaround leaves much to be desired.)One option for this is to add
with administrator privileges
in your AppleScript, but this requires manually typing in your password, defeating the purpose of automated backup. My current workaround is to:sudo visudo
and give my unprivileged user the ability to run my backup script as sudo with NOPASSWD: (I also specify the hash of the script to hopefully improve security, e.g.myuser ALL=(ALL) NOPASSWD: sha256:hashgoeshere /path/to/myscript.sh
)sudo chown root myscript.sh
sudo chmod 0740 myscript.sh
(4 so it can still be added to VCS)do shell script "sudo -n /path/to/myscript.sh"
and resave as MyApp.appFurther reading / details:
UPDATE:
After some preliminary testing, it looks like a slightly less hacky workaround is to compile a binary (using a compiled language) that calls your bash script. Add that binary to FDA and it seems to work. Add to the root-owned
/Library/LaunchDaemons
plist, and you have a way to call it fromroot
without all the craziness above.Example script in Go:
For security, I
sudo chown root
andsudo chmod 0700
the resulting binary before adding toFull Disk Access
(although admittedly an attacker could just change the bash script that this calls if it were left unprotected).