Background processing options for Mac App Store apps?

I'm busy designing my app's functionality and really would like to provide some features that rely on background processing after the user has logged in. A Login Item seems ideal for this use case.

I appreciate the lengths Apple go to, to communicate the complex technologies involved in app development, including the planning of macOS apps. I haven't found any information in the planning and design (admittedly under HIGs) documentation on whether it's possible to provide some background processing element along with an app destined for the Mac App Store. Perhaps it's not mentioned for a reason?

However, it would be really useful to background processing dealt with up-front, especially under planning, because it has a huge impact on how one moves forward with product design. Especially when you're an indy developer with limited time and resources.

I can't, for the life of me, find where I previously read that daemons and agents weren't allowed to be shipped with a Mac App Store app, because of the Sandbox requirements. It was probably a reply by Eskimo somewhere in the forums. Does the same apply to Login Items? The bulk of the Login Item documentation is in the documentation archive, most of which was written before the existence of the app stores, so I couldn't find any answers there. I previously believed that an app destined for the Mac App Store could only include a single binary, that of the main app itself. Although I've seen the recent article on including a command line utility binary in the distribution too.

Also, if my understanding of code signing is correct, apps distributed via an app store are signed by Apple, and thus can't communicate via XPC with a binary signed and distributed via a Developer ID. Or is there some workaround there that might get me closer to my goal?

An app for the Mac App Store must be a single app package, but that package can contain nested helpers of various kinds including app packages. And an app store app can contain a login item, but I was told that it can't be required. I think that's in the review guidelines somewhere. My app AutoPairs has radio buttons in the user interface, where one can choose to run the program only when the UI app is open, or always when logged it. I don't use XPC (I use distributed notifications and shared user defaults), but I think you can. You'll be signing the whole package, including any helpers, with the same app store signature.

JWWalker wrote:

I think that's in the review guidelines somewhere.

Check out clause 2.4.5(iii) of the App Review Guidelines.


alienspaces wrote:

I can't, for the life of me, find where I previously read that daemons and agents weren't allowed to be shipped with a Mac App Store app, because of the Sandbox requirements.

launchd daemons and agents are a different story. Daemons fall foul of clause 2.4.5(v). OTOH, agents don’t run as root and thus are fine. Indeed, we recently added an API, SMAppService, that makes installing this stuff much easier.

Your agent must be sandboxed, of course, but that’s not hard to do.

Does the same apply to Login Items?

Login items are also supported. A login item is subtlely different from a launchd agent. I generally prefer to use a launchd agent, but there are reasons to favour a login item. Most notably, if you support systems prior to macOS 13, where SMAppService was introduced, you have to use SMLoginItemSetEnabled, which yields a login item.

I previously believed that an app destined for the Mac App Store could only include a single binary, that of the main app itself.

That’s never been true. At a minimum, the Mac App Store has always supported helper tools. We even have a doc to explain how to set that up: Embedding a command-line tool in a sandboxed app.

And over the years this has expanded:

  • SMLoginItemSetEnabled in macOS 10.6

  • XPC services in… gosh… I’m not exactly sure but… macOS 10.7 IIRC

  • App extensions in macOS 10.10

  • System extensions in macOS 10.15

  • SMAppService in macOS 13

And probably others that I’ve forgotten (-:

apps distributed via an app store are signed by Apple, and thus can't communicate via XPC with a binary signed and distributed via a Developer ID.

No, that’s not right. Mac App Store apps must be sandboxed, and sandboxed apps have strict IPC limits. The general principle is that they can use IPC to communicate with other code from the same team. That includes both sandboxed and non-sandboxed code from that team.

For example, a launchd agent can use MachServices to publish a named XPC endpoint of the format GROUP_ID.NAME, where GROUP_ID is an app group ID and NAME is a name of its choosing. A sandboxed app can communicate with that endpoint as long as its entitled to use GROUP_ID. If the agent ships within a sandboxed app, it must also be sandboxed, and thus so entitled. If you distribute the agent directly, you get to choose whether or not to sandbox it.

IMPORTANT Before you start working with app groups, read App Groups: macOS vs iOS: Fight!.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Hi @eskimo

"we recently added an API, SMAppService, that makes installing this stuff much easier."

I was experimenting with that API yesterday. It's definitely very easy to use, thanks.

"At a minimum, the Mac App Store has always supported helper tools."

Recently I came across the macOS Planning Your App page, and was really impressed that it exists. I know there are a wealth of different Apple technologies and different styles of apps you can build with them, so it might be difficult to justify addressing this in a general way, but I can't help but think that it might be useful to others in the planning stage if Apple were to mention in the Planning your macOS app page what kind of helper tools are allowed on the Mac App Store, because it can have a huge effect on how you plan and what you design for, which can even make or break the user experience for certain types of apps, where background processing is a valuable feature. I did see the documentation on the embedded CLI tool thanks. I just assumed it was new. :-)

Thanks for the detailed feedback Eskimo, it's absolutely critical information for me.

Choosing between a launch agent and a login item, the thing that appeals to me about login items, is that the user can very easily confirm whether it is installed via System Settings, and they can easily remove it without me having to add some extra management code to my app for a launch agent.

A few questions from your feedback: Let's assume I choose what I feel is the path of least resistance, and embed a sandboxed login item in my app bundle. If the user chooses to give my app full disk access, would that access extend to the login item? If not, how would I go about ensuring that the login item full disk access status matches that of the main app? Would the same apply to a bundled launch agent? Thanks.

it might be useful to others in the planning stage if Apple were to mention in the Planning your macOS app page

The best way to get that feedback to the right people is to file a bug against that page.

Choosing between a launch agent and a login item … the user can very easily confirm whether [a login item] is installed via System Settings, and they can easily remove it without me having to add some extra management code to my app for a launch agent.

Correct. But keep clause 2.4.5(iii) in mind. I don’t work for App Review and can’t make definitive statements on their behalf, but my experience is that Mac App Store apps generally do include this UI as part of their user consent story.

Some other things that can help you choose here:

  • launchd agents have a lot more IPC options.

  • And can launch on demand.

  • Login items are not automatically relaunched if they crash or quit. You can configure your launchd agent to do that.

If the user chooses to give my app full disk access, would that access extend to [stuff installed with SMAppService]?

Yes. One of the key reasons we introduced SMAppService was to make it easier for us to track the responsibility relationship between disparate code items.

On the subject of Full Disk Access, remember that both a login item and launchd agent run as the logged in user, so FDA will help you with MAC checks but not with BSD permissions, ACLs, or the App Sandbox. For more on that topic, see On File System Permissions.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Hi @eskimo !

file a bug against that page.

Will do thanks!

"keep clause 2.4.5(iii) in mind." ... "Mac App Store apps generally do include this UI as part of their user consent story." ✓

Login items are not automatically relaunched if they crash or quit. You can configure your launchd agent to do that.

Righty-ho, a launch agent it shall be.

Thank you for your help. :-)

Background processing options for Mac App Store apps?
 
 
Q