Demystify code signing and its importance in app development. Get help troubleshooting code signing issues and ensure your app is properly signed for distribution.

All subtopics

Post

Replies

Boosts

Views

Activity

Fix CloudKit container permissions
I've been using CloudKit for my app recently and I'm trying to add support for a WatchOS app and I've enabled iCloud in capabilities and ticked the container I want to use but I get this error. CoreData: error: CoreData+CloudKit: -[NSCloudKitMirroringDelegate recoverFromPartialError:forStore:inMonitor:]block_invoke(1943): <NSCloudKitMirroringDelegate: 0x282430000>: Found unknown error as part of a partial failure: <CKError 0x28112d500: "Permission Failure" (10/2007); server message = "Invalid bundle ID for container"; uuid = ; container ID = "iCloud.Appname"> I tried creating a new container which worked for both the watch app and iOS app however I would like to use my original container since it has my old data
4
1
5k
Oct ’20
Can’t enforce safari as default browser
I would like to know on a mdm managed supervised device, how to force use Safari if a user has non-safari browser set as default. can enforcing safari for a domain or web clip be done? even shortcuts now, when using safari it opens whatever is set as default browser. Ironically if same simple shortcut of open URL with Chrome is created it opens with Chrome, regardless if default browser is set to firefox for example this default browser setting is great for personal use but cause issues now for corporate use for me anybody else figure this out? Also affects certificates for our managed devices
2
0
2.1k
Nov ’20
Unsatisfied entitlements: com.apple.logging.local-store
In my sandboxed MacOS app I want to access OSLogStore programmatically to fetch logs for multi-component application (app, libraries, deriver) for further analysis. According to the documentation, - https://developer.apple.com/documentation/oslog/oslogstore/3366102-local the app should have com.apple.logging.local-storeentitlement. I have added this entitlement "by hand" to the entitlement file as I I can't find a correspondent entry in the Xcode -> Sign & Capabilities interface. When I run the app, I get Unsatisfied entitlements: com.apple.logging.local-store error and the app doesn't start. If I remove the entitlement, the app can't get access to the logd subsystem. How can I add com.apple.logging.local-store to my app? Should I request this not visible via Xcode configuration UI from apple? Thanks!
4
0
1.2k
Nov ’20
Xcode CodeSigning Error
Hello, I am brand new to coding and developing. I have my Xcode compiled and linked to SFML correctly(finally), however there is one more error that just won't go away no matter what avenue I try or forum I read. I could use some advice from someone who is familiar with Xcode and Apple Code Signing problems. The error reads /Users/boundarybreaks/Library/Developer/Xcode/DerivedData/Timber2-fturuqxwvdaodsciwyrsjdepwzkr/Build/Products/Debug/Timber2.app: code object is not signed at all In subcomponent: /Users/boundarybreaks/Library/Developer/Xcode/DerivedData/Timber2-fturuqxwvdaodsciwyrsjdepwzkr/Build/Products/Debug/Timber2.app/Contents/Frameworks/vorbisenc.framework Command CodeSign failed with a nonzero exit code
3
0
2.5k
Jan ’21
How to delete certificates?
How to delete certificates from "Certificates, Identifiers &amp;amp; Profiles?" I have a new Mac and need to create new certificate for it but there is no option of deleting or editing of the existing certificates. When trying to add a new one the option is greyed out with the following commend: Developer ID Application This certificate is used to code sign your app for distribution outside of the Mac App Store. Maximum number of certificates generated.
7
1
8.9k
Feb ’21
Guideline 3.1.4 rejection
Hello all, I have an app that has been rejected due to Guideline 3.1.4 and I don't know how to get around it. The app is essentially a QR scanner for the construction industry that scans QR codes created by a plugin for design software. The app user can use the service completely free with no log in required. Once the QR code is scanned the app returns a result there are no features locked to the app user. The response form the review board is; Your app enables additional features or functionality when used with augmented reality markers or QR codes. However, those features are not available in the app to users without the necessary markers. Next Steps To resolve this issue, please provide a means to access these features from within the app, such as through achievements or in-app purchase. If they can be freely obtained, such as through a link to a website, please revise your app to include clear instructions for obtaining the necessary markers or codes. Which to me seems illogical because if the app user doesn't have a drawing with a QR code on it they don't need to use the app or know of its existence to find the result another way. The app user and the plugin user are two completely different entities and the app user would never be able to create or obtain the QR codes from the app without a drawing. The typical scenario would be the Architect would produce the drawings and add the QR code and give the drawings to the builder who would scan the QR code with the app to get a result. I am struggling to see how this differs to a generic QR scanner that is scanning a code on the side of a can of coke. Any assistance or advise would be appreciated.
1
0
1.1k
Mar ’21
Xcode 12.5 altool notarization failing intermittently
Since upgrading to Xcode 12.5, attempting to submit an app for notarization with /usr/bin/xcrun altool --notarize-app has started failing ~10% of the time with the error Upload succeeded but did not receive a RequestUUID.. Has anyone else encountered this issue? ?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 keyos-version/key string11.2.0/string keyproduct-errors/key array dict keycode/key integer-1018/integer keymessage/key stringUpload succeeded but did not receive a RequestUUID./string keyuserInfo/key dict keyNSLocalizedDescription/key stringUpload succeeded but did not receive a RequestUUID./string keyNSLocalizedFailureReason/key stringUnable to upload your app for notarization./string /dict /dict /array keytool-path/key string/Applications/Xcode.app/Contents/SharedFrameworks/ContentDeliveryServices.framework/Versions/A/Frameworks/AppStoreService.framework/string keytool-version/key string4.050.1210/string /dict /plist
13
0
3.1k
May ’21
No profiles for 'xxxx.app.development' were found: Xcode couldn't find any iOS App Development provisioning profiles matching 'xxxx.app.development'
I am trying to compile Xcode project on an online platform Bitrise. I am facing issue with sign in and provisioning .. after trying 4-5 days I am approaching you. Please solve this. ❌ error: No profiles for 'my app bundle id' were found: Xcode couldn't find any iOS App Development provisioning profiles matching 'my app bundle id'. Automatic signing is disabled and unable to generate a profile. To enable automatic signing, pass -allowProvisioningUpdates to xcodebuild. (in target 'myapp-Development' from project 'myapp') How to enable this "allowProvisioningUpdates" also why it is too difficult to do such processes with apple development.. I tried for android and it compiled successfully in a single attempt. please help.
5
0
8.9k
Jun ’21
Provisioning profile doesn't support the HealthKit capability, doesn't include com.apple.developer.healthkit and com.apple.developer.healthkit.access entitlements. Your account does not have sufficient permissions to modify containers.
When I try to add HealthKit capabilities to my app, I get the following signing errors: Communication with Apple failed. Your account does not have sufficient permissions to modify containers. Provisioning profile "iOS Team Provisioning Profile: com.domain.app" doesn't support the HealthKit capability. Provisioning profile "iOS Team Provisioning Profile: com.domain.app" doesn't include the com.apple.developer.healthkit and com.apple.developer.healthkit.access entitlements. In my developer account, the HK capability is enabled. And the entitlements needed are automatically generated by Xcode when I add HK capability, if I try to add them, it says they're already there. I have automatically managed signing selected. Clinical health records are not enabled for Health Kit. Common solutions like cleaning, derived data, and restarts don't help. Does anybody know what this is?
2
1
1.8k
Jul ’21
Transfer developer account to a new computer?
Hello, I've just got a new computer and now I want to transfer my developer account (certificates, keys etc.) to the new computer. Right now my developer membership has expired since I'm not doing any apps right now, but I might start again in the future. I'm not sure if I need to transfer anything, or if I will just get new certificates and keys when (if) I restart my membership? What do I need do, before I reset my old computer? I have developed apps for both for iOS and macOS.
4
1
2.2k
Sep ’21
notary tool fails on same file that altool notarizes successfully
Just got my brand new M1 Max laptop and am excited to get with the times and use notary tool instead of altool as recommended by the mothership but when I try to notarize the same file that altool notarizes successfully it fails. Here is is my sucessful altool command: xcrun altool --notarize-app --primary-bundle-id "My Kool Tool" --username "***@***.com" -p "@keychain:ac_notary" --asc-provider XXXXXXXXXXXX --file *.zip && rm *.zip and this is the notary tool command that fails on the same file: xcrun notarytool submit *.zip --keychain-profile "XXXXXX Apple Developer" --wait && rm *.zip Here is the output: Conducting pre-submission checks for archive.zip and initiating connection to the Apple notary service... Submission ID received  id: e20c0438-5576-4361-a11a-2efeb8exxxxx Successfully uploaded file  id: e20c0438-5576-4361-a11a-2efeb8exxxxx  path: /Users/***/Documents/archive.zip Waiting for processing to complete. Current status: Invalid.......... Processing complete  id: e20c0438-5576-4361-a11a-2efeb8exxxxx  status: Invalid and the log: xcrun notarytool log e20c0438-5576-4361-a11a-2efeb8exxxxx --keychain-profile "XXXXXX Apple Developer" {  "logFormatVersion": 1,  "jobId": "e20c0438-5576-4361-a11a-2efeb8exxxxx",  "status": "Invalid",  "statusSummary": "Archive contains critical validation errors",  "statusCode": 4000,  "archiveFilename": "archive.zip",  "uploadDate": "2021-12-07T18:57:23.193Z",  "sha256": "505d76b420d46bfd01d56c724de1c8d20121d75b0ca6cee96a51549708ec46ee",  "ticketContents": null,  "issues": [   {    "severity": "error",    "code": null,    "path": "archive.zip",    "message": "Package archive.zip has no signed executables or bundles. No tickets can be generated.",    "docUrl": null,    "architecture": null   }  ] } again, the same file notarizes with altool so it is properly signed It is worth noting that if I don't include the --asc-provider in the altool command it fails so maybe I just need to do the same with the notary tool but can't find any documentation on how to do that. Help Obi Wan
10
0
4.9k
Dec ’21
Notarization seems to succeed but installer has issues
It seems like something changed in the notarization in the last few days. I'm running the same build script that creates and notarize a DMG that contains a PKG with 4 plugins. Everything is signed correctly. No error anywhere in the notarization process. Checking the status of the notarization, I get this: Status: success Status Code: 0 Status Message: Package Approved Stapling returns this: The staple and validate action worked! Yet, if I check the PKG inside with this command: spctl -a -vvv -t install I get this output: .pkg: rejected source=Unnotarized Developer ID origin=Developer ID Installer: My Company This project was perfectly working a few weeks ago, and we have not changed a thing. Checking the notarization log, the only issue I see is this: "issues": [ { "severity": "warning", "code": null, "path": "Archive.dmg/Installer.pkg", "message": "This archive is corrupt, and cannot be unpacked for analysis.", "docUrl": null, "architecture": null } ] But this warning is also present in past DMG/PKG thatare notarized and work as they should. Another difference from previous logs is that I can only see one item in ticketContents, which is the DMG, while previously I could see two, both the DMG and the PKG.
1
0
771
Jan ’22
wkWebView, Trusted Domain, and Autofill/KeyChain Issue
We have been searching for almost one year for answers as to why wkWebView using an Entitled Domain will allow Autofill with KeyChain to fill credentials, but will not trigger Autofill to store/save them. In other words, if users have previously stored credentials in Safari while visiting domain X, subsequent visited to wkWebView with entitled domain X will allow use of those credentials in wkWebView through the Autofill/Keychain dialogue. However, users cannot save/store credentials within wkWebView in Trusted domain X because the save dialogue is never triggered.
3
0
1.9k
Feb ’22
Creating Distribution-Signed Code for Mac
IMPORTANT I’m very pleased to report that, due to the hard work of a number of folks at Apple, this DevForums post has been replaced by official documentation: Creating distribution-signed code for macOS. I’m leaving this post in place as a historical curiosity, but please consult the official documentation going forward. This post is one of a pair of posts, the other one being Packaging Mac Software for Distribution, that replaces my earlier Signing a Mac Product For Distribution post. Over the past year I’ve been trying to convert my most useful code signing posts here on DevForums to official documentation, namely: Placing Content in a Bundle Updating Mac Software Signing a Daemon with a Restricted Entitlement Embedding a Command-Line Tool in a Sandboxed App Embedding Nonstandard Code Structures in a Bundle Unfortunately in the past month or so my Day Job™, answering developer questions for DTS, has become super busy, and so I’ve not had chance to complete this work by publish a replacement for Signing a Mac Product For Distribution. This post, and Packaging Mac Software for Distribution, represent the current state of that effort. I think these are sufficiently better than Packaging Mac Software for Distribution to warrant posting them here on DevForums while I wait for the quiet time needed to finish the official work. Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" Creating Distribution-Signed Code for Mac Sign Mac code for distribution using either Xcode or command-line tools. Overview Before shipping a software product for the Mac, you must first create distribution-signed code, that is, code that you can package up and then submit to either the Mac App Store or the notary service. The way you do this depends on the nature of your product and how it was built: If your product is a standalone app, possibly with nested code such as an app extension, that you build using Xcode, use Xcode to export a distribution-signed app. If your product isn't a standalone app, but you build it using Xcode, create an Xcode archive, and then manually export distribution-signed code from that archive. If you build your product using an external build system, such as make, add a manual signing step to your build system. Once you have distribution-signed code, package it for distribution. For more information, see Packaging Mac Software for Distribution. Note If you use a third-party developer tool to build your app, consult its documentation for advice specific to that tool. Export an App from Xcode If your product is a standalone app that you build with Xcode, follow these steps to export a distribution-signed app: Build an Xcode archive from your project. Export a distribution-signed app from that Xcode archive. You can complete each step from the Xcode app or automate the steps using xcodebuild. To build an Xcode archive using the Xcode app, select your app’s scheme and choose Product > Archive. This creates the Xcode archive and selects it in the organizer. To create a distribution-sign app from that archive, select the archive in the organizer, click Distribute App, and follow the workflow from there. Note If the button says Distribute Content rather than Distribute App, your archive has multiple items in its Products directory. Make sure that every target whose output is embedded in your app has the Skip Install (SKIP_INSTALL) build setting set; this prevents the output from also being copied into the Xcode archive’s Products directory. For more on this, see TN3110 Resolving generic Xcode archive issue. For more information about the Xcode archives and the organizer, see Distributing Your App for Beta Testing and Releases. To build an Xcode archive from the command line, run xcodebuild with the archive action. Once you have an Xcode archive, export a distribution-signed app by running xcodebuild with the -exportArchive option. For more information about xcodebuild, see its man page. For instructions on how to read a man page, see Reading UNIX Manual Pages. For information about the keys supported by the export options property list, run xcodebuild with the -help argument. Export a Non-App Product Built with Xcode If you build your product with Xcode but it’s not a standalone app, you can build an Xcode archive using the techniques described in the previous section but you cannot export distribution-signed code from that archive. The Xcode organizer and the -exportArchive option only work for standalone apps. To export a distribution-signed product from the Xcode archive: Copy the relevant components from the archive. Sign those components manually. The exact commands for doing this vary depending on how your product is structured, so let’s consider a specific example. Imagine your product is a daemon but it also has an associated configuration app. Moreover, the configuration app has a share extension, and an embedded framework to share code between the app and the extension. When you build an Xcode archive from this project it has this structure: DaemonWithApp.xcarchive/ Info.plist Products/ usr/ local/ bin/ Daemon Applications/ ConfigApp.app/ Contents/ embedded.provisionprofile Frameworks/ Core.framework/ … PlugIns/ Share.appex/ Contents/ embedded.provisionprofile … … … The Products directory contains two items: the daemon itself (Daemon) and the configuration app (ConfigApp.app). To sign this product, first copy these items out of the archive: % mkdir "to-be-signed" % ditto "DaemonWithApp.xcarchive/Products/usr/local/bin/Daemon" "to-be-signed/Daemon" % ditto "DaemonWithApp.xcarchive/Products/Applications/ConfigApp.app" "to-be-signed/ConfigApp.app" IMPORTANT When you copy code, use ditto rather than cp. ditto preserves symlinks, which are critical to the structure of Mac frameworks. For more information on this structure, see Placing Content in a Bundle. Symlinks are also useful when dealing with nonstandard code structures. For more details, see Embedding Nonstandard Code Structures in a Bundle. The code you copy from the Xcode archive is typically development-signed: % codesign -d -vv to-be-signed/Daemon … Authority=Apple Development: … … To ship this code, you need to re-sign it for distribution. Confirm Your Code Signing Identity To sign code for distribution you need a code signing identity. Choose the right identity for your distribution channel: If you’re distributing an app on the Mac App Store, use an Apple Distribution code signing identity. This is named Apple Distribution: TTT, where TTT identifies your team. Alternatively, you can use the old school Mac App Distribution code signing identity. This is named 3rd Party Mac Developer Application: TTT, where TTT identifies your team. If you’re distributing a product independently, use a Developer ID Application code signing identity. This is named Developer ID Application: TTT, where TTT identifies your team. For information on how to set up these code signing identities, see Developer Account Help. To confirm that your code-signing identity is present and correct, run the following command: % security find-identity -p codesigning -v 1) A06E7F3F8237330EE15CB91BE1A511C00B853358 "Apple Distribution: …" 2) ADC03B244F4C1018384DCAFFC920F26136F6B59B "Developer ID Application: …" 2 valid identities found The -p codesigning argument filters for code-signing identities. The -v argument filters for valid identities only. If the code-signing identity that you need isn't listed, see Developer Account Help. Each output line includes a SHA-1 hash that uniquely identifies the identity. If you have multiple identities with the same name, sign your code using this hash rather than the identity name. Identify the Code to Sign To sign your product, first identify each code item that you need to sign. For example, in the DaemonWithApp product, there are four code items: ConfigApp.app, Core.framework, Share.appex, and Daemon. For each code item, determine the following: Is it bundled code? Is it a main executable? IMPORTANT For a code item to be considered bundled code it must be the main code within a bundle. If, for example, you have an app with a nested helper tool, there are two code items: the app and the helper tool. The app is considered bundle code but the helper tool is not. In some cases, it might not be obvious whether the code item is a main executable. To confirm, run the file command. A main executable says Mach-O … executable. For example: % file "to-be-signed/ConfigApp.app/Contents/Frameworks/Core.framework/Versions/A/Core" … … Mach-O 64-bit dynamically linked shared library x86_64 … % file "to-be-signed/ConfigApp.app/Contents/PlugIns/Share.appex/Contents/MacOS/Share" … … Mach-O 64-bit executable x86_64 … The Core.framework is not a main executable but Share.appex is. To continue the DaemonWithApp example, here’s a summary of this info for each of its code items: | Code Item | Bundled Code? | Main Executable | | --------- | ------------- | --------------- | | ConfigApp.app | yes | yes | | Core.framework | yes | no | | Share.appex | yes | yes | | Daemon | no | yes | Determine the Signing Order Sign code from the inside out. That is, if A depends on B, sign B before you sign A. For the DaemonWithApp example, the signing order for the app is: Core.framework Share.appex ConfigApp.app The app and daemon are independent, so you can sign them in either order. Configure Your Entitlements A code signature may include entitlements. These key-value pairs grant an executable permission to use a service or technology. For more information about this, see Entitlements. Entitlements only make sense on a main executable. When a process runs an executable, the system grants the process the entitlements claimed by its code signature. Do not apply entitlements to library code. It doesn’t do anything useful and can prevent your code from running. When signing a main executable, decide whether it needs entitlements. If so, create an entitlements file to use when signing that executable. This entitlements file is a property list containing the key-value pairs for the entitlements that the executable claims. If you build your product with Xcode, you might be able to use the .entitlements file that Xcode manages in your source code. If not, create the .entitlements file yourself. IMPORTANT The entitlements file must be a property list in the standard XML format with LF line endings, no comments, and no BOM. If you’re not sure of the file’s provenance, use plutil to convert it to the standard format. For specific instructions, see Ensure Properly Formatted Entitlements. If you have a development-signed version of your program you can get a head start on this by dumping its entitlements. For example: % codesign -d --entitlements - --xml "to-be-signed/ConfigApp.app" | plutil -convert xml1 -o - - … <dict> <key>com.apple.application-identifier</key> <string>SKMME9E2Y8.com.example.apple-samplecode.DaemonWithApp.App</string> <key>com.apple.developer.team-identifier</key> <string>SKMME9E2Y8</string> <key>com.apple.security.app-sandbox</key> <true/> <key>keychain-access-groups</key> <array> <string>SKMME9E2Y8.com.example.apple-samplecode.DaemonWithApp.SharedKeychain</string> </array> </dict> </plist> Keep in mind that some entitlements vary between development and distribution builds. For example: The value of the APS Environment (macOS) Entitlement changes from development to production. The com.apple.security.get-task-allow entitlement allows the debugger to attach to your program, so you rarely apply it to a distribution-signed program. To check whether an entitlement varies in distribution builds, see the documentation for that specific entitlement in Entitlements. For information about when it makes sense to distribute a program signed with the get-task-allow entitlement, see Avoid the Get-Task-Allow Entitlement section in Resolving Common Notarization Issues). Embed Distribution Provisioning Profiles In general, all entitlement claims must be authorized by a provisioning profile. This is an important security feature. For example, the fact that the keychain-access-groups entitlement must be authorized by a profile prevents other developers from shipping an app that impersonates your app in order to steal its keychain items. However, macOS allows programs to claim some entitlements without such authorization. These unrestricted entitlements include: com.apple.security.get-task-allow com.apple.security.application-groups Those used to enable and configure the App Sandbox Those used to configure the Hardened Runtime If your program claims a restricted entitlement, include a distribution provisioning profile to authorize that claim: Create the profile on the developer web site. Copy that profile into your program’s bundle. Note If your product includes a non-bundled executable that uses a restricted entitlement, package that executable in an app-like structure. For details on this technique, see Signing a Daemon with a Restricted Entitlement. To create a distribution provisioning profile, follow the instructions in Developer Account Help. Make sure to choose a profile type that matches your distribution channel (Mac App Store or Developer ID). Once you have a distribution provisioning profile, copy it into your program’s bundle. For information about where to copy it, see Placing Content in a Bundle. To continue the DaemonWithApp example, the configuration app and its share extension use a keychain access group to share secrets. The system grants the programs access to that group based on their keychain-access-groups entitlement claim, and such claims must be authorized by a provisioning profile. The app and the share extension each have their own profile. To distribute the app, update the app and share extension bundles with the corresponding distribution provisioning profile: % cp "ConfigApp-Dist.provisionprofile" "to-be-signed/ConfigApp.app/Contents/embedded.provisionprofile" % cp "Share-Dist.provisionprofile" "to-be-signed/ConfigApp.app/Contents/PlugIns/Share.appex/Contents/embedded.provisionprofile" Modifying the app in this way will break the seal on its code signature. This is fine because you are going to re-sign the app before distributing it. IMPORTANT If you’re building your product with Xcode then you might find that Xcode has embedded a provisioning profile within your bundle. This is a development provisioning profile. You must replace it with a distribution provisioning profile. Sign Each Code Item For all code types, the basic codesign command looks like this: % codesign -s III PPP Here III is the name of the code signing identity to use and PPP is the path to the code to sign. The specific identity you use for III varies depending on your distribution channel, as discussed in Confirm Your Code Signing, above. Note If you have multiple identities with the same name, supply the identity’s SHA-1 hash to specify it unambiguously. For information on how to get this hash, see Confirm Your Code Signing, above. When signing bundled code, as defined in Identify the Code to Sign, above, use the path to the bundle for PPP, not the path to the bundle’s main code. If you’re re-signing code — that is, the code you’re signing is already signed — add the -f option. If you’re signing a main executable that needs entitlements, add the --entitlements EEE option, where EEE is the path to the entitlements file for that executable. For information on how to create this file, see Configure Your Entitlements, above. If you’re signing for Developer ID distribution, add the --timestamp option to include a secure timestamp. If you’re signing a main executable for Developer ID distribution, add the -o runtime option to enable the Hardened Runtime. For more information about the Hardened Runtime, see Hardened Runtime. If you’re signing non-bundled code, add the -i BBB option to set the code signing identifier. Here BBB is the bundle ID the code would have if it had a bundle ID. For example, if you have an app whose bundle ID is com.example.flying-animals that has a nested command-line tool called pig-jato, the bundle ID for that tool would logically be com.example.flying-animals.pig-jato, and that’s a perfectly fine value to use for BBB. Note For bundled code, you don’t need to supply a code signing identifier because codesign defaults to using the bundle ID. Repeat this signing step for every code item in your product, in the order you established in Determine the Signing Order, above. If you have a complex product with many code items to sign, create a script to automate this process. Here's the complete sequence of commands to sign the DaemonWithApp example for Developer ID distribution: % codesign -s "Developer ID Application" -f --timestamp "to-be-signed/ConfigApp.app/Contents/Frameworks/Core.framework" to-be-signed/ConfigApp.app/Contents/Frameworks/Core.framework: replacing existing signature % codesign -s "Developer ID Application" -f --timestamp -o runtime --entitlements "Share.entitlements" "to-be-signed/ConfigApp.app/Contents/PlugIns/Share.appex" to-be-signed/ConfigApp.app/Contents/PlugIns/Share.appex: replacing existing signature % codesign -s "Developer ID Application" -f --timestamp -o runtime --entitlements "ConfigApp.entitlements" "to-be-signed/ConfigApp.app" to-be-signed/ConfigApp.app: replacing existing signature % codesign -s "Developer ID Application" -f --timestamp -o runtime -i "com.example.apple-samplecode.DaemonWithApp.Daemon" "to-be-signed/Daemon" to-be-signed/Daemon: replacing existing signature Consider Deep Harmful When signing code, do not pass the --deep option to codesign. This option is helpful in some specific circumstances but it will cause problems when signing a complex product. Specifically: It applies the same code signing options to every code item that it signs, something that’s not appropriate. For example, you might have an app with an embedded command-line tool, where the app and the tool need different entitlements. The --deep option will apply the same entitlements to both, which is a serious mistake. It only signs code that it can find, and it only finds code in nested code sites. If you put code in a place where the system is expecting to find data, --deep won’t sign it. The first issue is fundamental to how --deep works, and is the main reason you should avoid it. The second issue is only a problem if you don’t follow the rules for nesting code and data within a bundle, as documented in Placing Content in a Bundle. Revision History 2024-02-19 Added a preamble that links to the official documentation, Creating distribution-signed code for macOS. 2022-08-17 Updated the Confirm Your Code Signing Identity section to cover Apple Distribution code signing identities. Added a link to TN3110. 2022-03-01 First posted.
0
0
8.2k
Mar ’22
Packaging Mac Software for Distribution
IMPORTANT I’m very pleased to report that, due to the hard work of a number of folks at Apple, this DevForums post has been replaced by official documentation: Packaging Mac software for distribution. I’m leaving this post in place as a historical curiosity, but please consult the official documentation going forward. This post is one of a pair of posts, the other one being Creating Distribution-Signed Code for Mac, that replaces my earlier Signing a Mac Product For Distribution post. For more background on this, see the notes at the top of Creating Distribution-Signed Code for Mac. Share and Enjoy — Quinn “The Eskimo!” @ Developer Technical Support @ Apple let myEmail = "eskimo" + "1" + "@" + "apple.com" Packaging Mac Software for Distribution Build a zip archive, disk image, or installer package for distributing your Mac software. Overview Xcode is a great tool for creating and distributing Mac apps. Once you’ve written your code you can upload it to the App Store with just a few clicks. However, Xcode cannot do everything. For example: Some Mac software products are not apps. You might, for example, be creating a product that includes a daemon. Some Mac products include multiple components. Your daemon might include an app to configure it. Some Mac products ship outside of the App Store, and so need to be packaged for distribution. For example, you might choose to distribute your daemon and its configuration app in an installer package. Some Mac products are built with third-party developer tools. If your product cannot be built and distributed using Xcode alone, follow these instructions to package it for distribution. Note If you use a third-party developer tool to build your app, consult its documentation for advice specific to that tool. To start this process you need distribution-signed code. For detailed advice on how to create distribution-signed code, see Creating Distribution-Signed Code for Mac. If you ship your product frequently, create a script to automate the distribution process. Decide on a Container Format To get started, decide on your container format. Mac products support two distribution channels: The Mac App Store, for apps Independent distribution, for apps and non-apps, using Developer ID signing A Mac App Store app must be submitted as an installer package. In contrast, products distributed outside of the Mac App Store use a variety of different container formats, the most common being: Zip archive (.zip) Disk image (.dmg) Installer package (.pkg) You may choose to nest these containers. For example, you might ship an app inside an installer package on a disk image. Nesting containers is straightforward: Just work from the inside out, following the instructions for each container at each step. IMPORTANT Sign your code and each nested container (if the container supports signing). For example, if you ship an app inside an installer package on a disk image, sign the app, then create the installer package, then sign that package, then create the disk image, then sign the disk image. Each container format has its own pros and cons, so choose an approach based on the requirements of your product. Build a Zip Archive If you choose to distribute your product in a zip archive, use the ditto tool to create that archive: Create a directory that holds everything you want to distribute. Run the ditto tool as shown below, where DDD is the path to the directory from step 1 and ZZZ is the path where ditto creates the zip archive. % ditto -c -k --keepParent DDD ZZZ Zip archives cannot be signed, although their contents can be. Build an Installer Package If you choose to distribute your product in an installer package, start by determining your installer signing identity. Choose the right identity for your distribution channel: If you’re distributing an app on the Mac App Store, use a Mac Installer Distribution signing identity. This is named 3rd Party Mac Developer Installer: TTT, where TTT identifies your team. If you’re distributing a product independently, use a Developer ID Installer signing identity. This is named Developer ID Installer: TTT, where TTT identifies your team. For information on how to set up these installer signing identities, see Developer Account Help. Run the following command to confirm that your installer signing identity is present and correct: % security find-identity -v 1) 6210ECCC616B6A72F238DE6FDDFDA1A06DEFF9FB "3rd Party Mac Developer Installer: …" 2) C32E0E68CE92936D5532E21BAAD8CFF4A6D9BAA1 "Developer ID Installer: …" 2 valid identities found The -v argument filters for valid identities only. If the installer signing identity you need is not listed, see Developer Account Help. IMPORTANT Do not use the -p codesigning option to filter for code signing identities. Installer signing identities are different from code signing identities and the -p codesigning option filters them out. If your product consists of a single app, use the productbuild tool to create a simple installer package for it: % productbuild --sign III --component AAA /Applications PPP In this command: III is your installer signing identity. AAA is the path to your app. PPP is the path where productbuild creates the installer package. The above is the simplest possible use of productbuild. If you’re submitting an app to the Mac App Store, that’s all you need. If you have a more complex product, you’ll need a more complex installer package. For more details on how to work with installer packages, see the man pages for productbuild, productsign, pkgbuild, and pkgutil. For instructions on how to read a man page, see Reading UNIX Manual Pages. Build a Disk Image If you choose to distribute your product in a disk image: Create a directory to act as the source for the root directory of your disk image’s volume. Populate that directory with the items you want to distribute. If you’re automating this, use ditto rather than cp because ditto preserves symlinks. Use hdiutil command shown below to create the disk image, where SSS is the directory from step 1 and DDD is the path where hdiutil creates the disk image. Decide on a code signing identifier for this disk image. If you were signing bundled code, you’d use the bundle ID as the code signing identifier. However, disk images have no bundle ID and thus you must choose a code signing identifier for your image. For advice on how to do this, see the Sign Each Code section in Creating Distribution-Signed Code for Mac. Use the codesign command shown below to sign the disk image, where III is your Developer ID Application code signing identity (named Developer ID Application: TTT, where TTT identifies your team), BBB is the code signing identifier you chose in the previous step, and DDD is the path to the disk image from step 3. % hdiutil create -srcFolder SSS -o DDD % codesign -s III --timestamp -i BBB DDD For more information on code signing identities, see the Confirm Your Code Signing section in Creating Distribution-Signed Code for Mac. IMPORTANT Sign your disk image with a code signing identity, not an installer signing identity. There are various third-party tools that configure a disk image for distribution. For example, the tool might arrange the icons nicely, set a background image, and add a symlink to the Applications folder. If you use such a tool, or create your own tool for this, make sure that the resulting disk image: Is signed with your Developer ID Application code signing identity Is a UDIF-format read-only zip-compressed disk image (type UDZO) Submit Your App to the Mac App Store If you’re creating an app for the Mac App Store, submit your signed installer package using either the altool command-line tool or the Transporter app. For detailed instructions, see App Store Connect Help > Reference > Upload tools. Notarize Your Product If you’re distributing outside of the Mac App Store, notarize the file you intend to distribute to your users. For detailed instructions, see Customizing the Notarization Workflow. Skip the Export a Package for Notarization section because you already have the file that you want to submit. If you’re using nested containers, only notarize the outermost container. For example, if you have an app inside an installer package on a disk image, sign the app, sign the installer package, and sign the disk image, but only notarize the disk image. The exception to this rule is if you have a custom third-party installer. In that case, see the discussion in Customizing the Notarization Workflow. Staple Your Product Once you’ve notarized your product, staple the resulting ticket to the file you intend to distribute. Staple the Ticket to Your Distribution discusses how to do this for an app within a zip archive. The other common container formats, installer packages and disk images, support stapling directly. For example, to staple a tick to a disk image: % xcrun stapler staple FlyingAnimals.dmg Stapling is recommended but not mandatory. However, if you don’t staple a user might find that your product is blocked by Gatekeeper if they try to install or use it while the Mac is offline. Revision History 2024-02-19 Added a preamble that links to the official documentation, Packaging Mac software for distribution. 2022-03-01 First posted.
0
0
7.7k
Mar ’22
carplay-audio entitlement missing from provisioning profile
When I download my provisioning profile I can't find the com.apple.developer.carplay-audio entitlement in it. Here's what I did: For our app identifier on Apple Developer Portal in "Additional Capabilities" I enabled "CarPlay Audio App (CarPlay framework)". After that I generated a provisioning profile and downloaded it. In the provisional profile info on Apple Developer Portal I can see "CarPlay Audio App (CarPlay framework)" in "Enabled Capabilities". When I import the downloaded profile in Xcode, I can't see the CarPlay entitlement there. After I added the "com.apple.developer.carplay-audio" entitlement to my .entitlements file, I'm getting the "Provisioning profile ... doesn't include the com.apple.developer.carplay-audio entitlement.". When I'm opening the profile in my text editor, I also can't find "carplay-audio" there. Is there a way to solve this problem?
6
0
3k
Mar ’22
"Invalid Bundle. The bundle <bundle name> does not support the minimum OS Version specified in the Info.plist"
I have been working with a framework to add multiplayer support to my app. The app runs on test devices, simulators, and archives perfectly fine and the app is fine without the framework. But when I go to distribute the app, I see get this error related to the multiplayer framework I have added. I have tried updating the minimumOSVersion to 9.0, 10.0, 12.0, and 13.0 everywhere (info.plist, deployment info, build settings, etc) and they all match with each build/archive but no matter what I can't get fix this error. This error only shows up when I go to distribute the app to the store. Any ideas on what to try or how to fix this issue? I've attached a screenshot of the issue below.
10
3
11k
May ’22