16

I'm making a sandboxed Mac app, and I used NSOpenPanel to get a file URL, and saved it to UserDefaults as a security-scoped bookmark. When I quit and restart the app, I can resolve that blob of Data into a URL again.

The documentation says I should call startAccessingSecurityScopedResource(), and check its return value. (That does return true when I call it.) But if I don't call that, I've still got a resolved URL, and I still appear to have permissions to access it.

What does startAccessingSecurityScopedResource() actually do? Is there anything bad that can happen, if I don't call it?

Ssswift
  • 916
  • 10
  • 20
  • 1
    Update: I've had an app in the Mac App Store for several months, through at least half a dozen different versions. This app never calls `startAccessingSecurityScopedResource()`, yet neither the Apple reviewers nor any of my users have reported a single issue with accessing files or folders. – Ssswift May 22 '17 at 17:09

1 Answers1

7

As long as your app only accesses files in standard locations (Downloads, Music Movies, Pictures) and you included the required entitlements for programmatic file and folder access in your app, you don't need to store security scoped bookmarks for those locations.

But for other locations that should remain accessible after the app has been restarted, you should store security scoped bookmarks and call startAccessingSecurityScopedResource() before access. If you skip that step, you'll get an exception as soon as you try to access that file.

startAccessingSecurityScopedResource() makes the security scoped bookmark's resource available to your app's sandbox thus granting you access to that resource.

seb
  • 2,350
  • 24
  • 30
  • "If you skip that step, you'll get an exception as soon as you try to access that file." As I stated in the question, no, I don't. Are you seeing this behavior? What version of macOS are you using? – Ssswift Mar 10 '18 at 19:36
  • 1
    @Ssswift Here is a gist to reproduce the crash: https://gist.github.com/anonymous/ef56f55e0e9eb8da8d0514644a5c11b8 (Xcode 9.2, macOS 10.13.3) – seb Mar 12 '18 at 10:38
  • Thanks, I'll check it out when I have time. From glancing at your code, I see that you're using "/tmp", though, which is a funny case with the Mac sandbox, because it's a symlink into "/private". Lots of things behave very strangely if you try using /tmp with the sandbox. – Ssswift Mar 16 '18 at 19:08
  • 5
    I ran into this issue as well and it was not obvious at first how this all worked. I blogged about it here: https://benscheirman.com/2019/10/troubleshooting-appkit-file-permissions/ – Ben Scheirman Oct 23 '19 at 23:45