Skip to content

Instantly share code, notes, and snippets.

@dpid
Last active December 6, 2023 20:42
Show Gist options
  • Star 98 You must be signed in to star a gist
  • Fork 9 You must be signed in to fork a gist
  • Save dpid/270bdb6c1011fe07211edf431b2d0fe4 to your computer and use it in GitHub Desktop.
Save dpid/270bdb6c1011fe07211edf431b2d0fe4 to your computer and use it in GitHub Desktop.
How to notarize a Unity build for MacOs 10.15 Catalina

How to notarize a Unity build for macOs 10.15 Catalina

As of January 2020, all apps running on macOs 10.15 Catalina are required to be notarized. For Unity games distributed outside the Mac App Store, such as with Steam, the notarization process is done post build using a series of Xcode command line tools.

Prerequisites

  • a Mac that is compatible with macOs 10.15 Catalina :
    • MacBook (2015 or newer)
    • MacBook Air (2012 or newer)
    • MacBook Pro (2012 or newer)
    • Mac mini (2012 or newer)
    • iMac (2012 or newer)
    • iMac Pro (from 2017)
    • Mac Pro (2013 or newer)
  • macOs 10.15 Catalina installed
  • Xcode 11.0 installed
  • Apple developer account at https://developer.apple.com/
  • Apple Id account at https://appleid.apple.com

Developer ID Application certificate

This certificate will be used for code signing the build. If you don't already have one, you can create one in the account section of the Apple developer website https://developer.apple.com/account/resources/certificates/add

In the "Create a New Certificate" section, select to add a "Developer ID Application" certificate. After clicking continue, you should see further instructions about how you'll first need to create and upload a "Certificate Signing Request" using the Keychain Access app https://help.apple.com/developer-account/#/devbfa00fef7

After you've uploaded the Certificate Signing Request file, you should then be able to download the Developer Id Application certificate. Once downloaded, clicking on the file should add it to Keychain Access where you'll see it under the certificates section. It will be called something like "Developer ID Applicate : YourCompanyName (0123456789)"

Generated Password

To upload a build to Apple servers you'll need to use a "generated password". To create one, go to https://appleid.apple.com and then in the "Security" section click on "Generated Password..."

The password you generate will look similar to the format abcd-efgh-ijkl-mnop

Unity Build & Player Settings

  • In the Build Settings, target platform should be set to Mac OS
  • In Player Settings, use default settings and set a unique Bundle Identifier

Entitlements file

This is an xml file used to give executable permissions to the app when code signing. In particular, all apps need to have "Hardened Runtime" entitlements. Here are the minimum entitlements needed for a Unity build :

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
    <dict>
	       <key>com.apple.security.cs.disable-library-validation</key>
	       <true/>
	       <key>com.apple.security.cs.disable-executable-page-protection</key>
	       <true/>
    </dict>
</plist>

Save this file as "YourGame.entitlements". Additional entitlements can be found at https://developer.apple.com/documentation/bundleresources/entitlements

Notarization

The following steps use the Terminal command line and assume your build and entitlements file are in the same directory.

Change all file permissions in the app

For the code signing to work in a later step, we need to change permissions for files within the app directory.

chmod -R a+xr "YourGame.app"

Code sign the app

Next, in the command line, we need to use the codesign tool on the permission changed files by using your Developer ID Application certificate (literally the name of the certificate in double quotes).

codesign --deep --force --verify --verbose --timestamp --options runtime --entitlements "YourGame.entitlements" --sign "Developer ID Application : YourCompanyName (0123456789)" "YourGame.app"

If successful, you should see a message similar to:

YourGame.app: signed app bundle with Mach-O thin (x86_64) [com.YourCompany.YourGame]

Create a zip

Once the code is signed, we need to compress the application into a zip file for uploading. You can do this in the command line.

ditto -c -k --sequesterRsrc --keepParent "YourGame.app" "YourGame.zip"

Upload the zip to Apple's notarization service

Now that we have the compressed zip file, we'll want to upload it to the Apple servers for notarization using the xcrun altool in the command line. In order to do this, you'll need your Apple ID username (usually an email address), your Apple ID generated password (the one with the format abcd-efgh-ijkl-mnop) and your Apple Developer "Provider Short Name". Often the "Provider Short Name" is your Team ID (ten digit alphanumeric id), you can find in the membership section of your Apple developer account https://developer.apple.com/account/#/membership/

However, if your "Provider Short Name" is not the same as your Team ID, you can find it by running the following command:

xcrun iTMSTransporter -m provider -u YourAppleIDUsername -p abcd-efgh-ijkl-mnop

Also, you'll need your game's bundle id that you defined in Unity Player Settings. Usually the format for that is similar to com.YourCompany.YourGame

To upload the build to the notarization service, run the command:

xcrun altool --notarize-app --username YourAppleIDUsername --password abcd-efgh-ijkl-mnop --asc-provider ProviderShortName --primary-bundle-id com.YourCompany.YourGame --file YourGame.zip

If the upload was successful, you should see a message with a RequestUUID similar to:

No errors uploading 'YourGame.zip'.
RequestUUID = xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx

From there, you will need to wait for the notarization service to process the upload. This can take anywhere from 1 minute to an hour or sometimes longer if the service is overloaded. When it's completed you'll get an email with the subject "Your Mac software was successfully notarized". Alternatively, you can ping the service for the current status of the upload using that RequestUUID by running the following command.

xcrun altool --notarization-info xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx --username YourAppleIDUsername --password abcd-efgh-ijkl-mnop --asc-provider YourAppleDeveloperTeamID

Staple the app

After notarization is completed, Apple creates a ticket that you need to "staple" to the app. To do that, we'll use the xcrun stapler tool.

xcrun stapler staple "YourGame.app"

If successful you should see the following message:

The staple and validate action worked!

Check notarization

After everything is completed we can use the spctl tool to check if the app is recognized as having the proper notarization.

spctl -a -v YourGame.app

If successful, you should see a message similar to:

YourGame.app: accepted
source=Notarized Developer ID

Now, whether or not the notarization was successful, if you try and open the app on your local machine, everything will appear to work fine. A good way to double check everything is actually working is to upload the notarized build to somewhere on the web (eg Google Drive), download it, and then see if the app opens properly. If working correctly, then all you should see is a small warning that you downloaded it from the web and then it should open normally.

@MashupGamingDKK
Copy link

MashupGamingDKK commented Jun 17, 2021

Everything goes as described, but the resulting app gives a "You do not have permission to open the application “(app name)”, Contact your computer or network administrator for assistance". error when you launch it

Same thing happened to me, I found out it is something caused by codesign with a bad entitlements, I am still not sure what is the correct entitlements but I found this little asset made by someone else.

https://github.com/cunum/unity-osx-notarize

edited: the password refers to the generated password, not your apple id password, should be something like aaaa-bbbb-cccc-dddd
It worked for me.

Some other related material should be on this https://forum.unity.com/threads/notarizing-osx-builds.588904/

The writer for this article also replied something on the above forum.

Hope it can help you even after so long time.

@Can0nC
Copy link

Can0nC commented Oct 25, 2021

Hi everyone, I was able to go through the process and successfully notarize the app. But unfortunately, for some reason, it broke the app, which lead to the error DllNotFoundException: Unable to load DLL 'agoraSdkCWrapper': The specified module could not be found. (The app was able to run without any error before notarization).

Any help or suggestions? Thank you!

@Cjericho4
Copy link

I made a Makefile based on other comments made here that uses the codesign command given by @ThunderboxEntertainment as that was the only one that would work for the app that we made, I also found that if you only run the first command that he gives you can notarize without signing the application itself. You can find the Makefile here: https://github.com/Cjericho4/UnityMacBuildSigner

@cuikeqiang
Copy link

Try sign every bundle in your "xxx.app".
Something like:

ITEMS=""
PLUGIN_DIR="${app_file}/Contents"
if [ -d "$PLUGIN_DIR" ] ; then
PLUGIN=$(find "${PLUGIN_DIR}" -depth -type d -name ".framework" -or -name ".dylib" -or -name "*.bundle" | sed -e "s/(.*framework)/\1/Versions/A//")
RESULT=$?
if [[ $RESULT != 0 ]] ; then
exit 1
fi

ITEMS="${PLUGIN}"

fi

ITEMS="${ITEMS}"$'\n'"${app_file}"

echo "Found:"
echo "${ITEMS}"

for ITEM in $ITEMS;
do
if [[ ${ITEM} == BUNDLE_YOU_WANT_TO_SKIP ]] ; then
echo "Skip '${ITEM}'"
continue
fi

echo "Signing '${ITEM}'"

/usr/bin/codesign --force -s "${sig}" --options runtime "${ITEM}" -v --entitlements "YOUR_ENTITLEMENTS_FILE.entitlements"
RESULT=$?
if [[ $RESULT != 0 ]] ; then
    echo "Failed to sign '${ITEM}'."
    exit 1
fi

done

@SharkWithLasers
Copy link

On my machine, I got a Code Sign Error "resource fork, Finder information, or similar detritus not allowed" when running the codesign -deep ... command.

In order to fix this, I had to run xattr -cr <path_to_project_dir> before the codesign command. (<path_to_project_dir> is the .app directory). (from here: https://stackoverflow.com/questions/39652867/code-sign-error-in-macos-monterey-xcode-resource-fork-finder-information-or)

Hope that helps others!

@Colbydude
Copy link

Colbydude commented Dec 6, 2023

Note sure if there's an updated version of this around, but I've followed the steps for the most part and was able to successfully switch to Apple's new notarytool to get my game notarized. Apple has deprecated the altool. So here's what I did:

  • Followed all the steps up to "Upload the zip to Apple's notarization service"
  • At the "Upload the zip to Apple's notarization service" step, I then leverage notarytool instead of altool by doing the following:
# Cache credentials in the keychain so you can just specify a --keychain-profile in subsequent commands.
# Provide whatever you like for <credential-name>, maybe YourGame-notary-credentials.
xcrun notarytool store-credentials "<credential-name>" --apple-id "<apple id>" --team-id <team id> --password <app-password>

# Upload the zip to the notarization service. This may take a while.
xcrun notarytool submit YourGame.zip --keychain-profile "<credential-name>" --wait

# If the command exits, or you want to check the status of your upload,
# this will attempt to get the status and write it to a file called developer_log.json
# Use the UUID returned back from the previous command.
xcrun notarytool log xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx --keychain-profile "<credential-name>" developer_log.json
  • Finally, continue on with "Staple the app"

Hopefully this helps anyone who may stumble across this gist!

Some more info here:
https://developer.apple.com/documentation/technotes/tn3147-migrating-to-the-latest-notarization-tool
https://developer.apple.com/documentation/security/notarizing_macos_software_before_distribution/customizing_the_notarization_workflow?language=objc

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment