Prioritize user privacy and data security in your app. Discuss best practices for data handling, user consent, and security measures to protect user information.

All subtopics
Posts under Privacy & Security topic

Post

Replies

Boosts

Views

Activity

How to use an Intune-delivered SCEP certificate for mTLS in iOS app using URLSessionDelegate?
I am working on implementing mTLS authentication in my iOS app (Apple Inhouse & intune MAM managed app). The SCEP client certificate is deployed on the device via Intune MDM. When I try accessing the protected endpoint via SFSafariViewController/ASWebAuthenticationSession, the certificate picker appears and the request succeeds. However, from within my app (using URLSessionDelegate), the certificate is not found (errSecItemNotFound). The didReceive challenge method is called, but my SCEP certificate is not found in the app. The certificate is visible under Settings > Device Management > SCEP Certificate. How can I make my iOS app access and use the SCEP certificate (installed via Intune MDM) for mTLS requests? Do I need a special entitlement, keychain access group, or configuration in Intune or Developer account to allow my app to use the certificate? Here is the sample code I am using: final class KeychainCertificateDelegate: NSObject, URLSessionDelegate { func urlSession(_ session: URLSession, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) { guard challenge.protectionSpace.authenticationMethod == NSURLAuthenticationMethodClientCertificate else { completionHandler(.performDefaultHandling, nil) return } // Get the DNs the server will accept guard let expectedDNs = challenge.protectionSpace.distinguishedNames else { completionHandler(.cancelAuthenticationChallenge, nil) return } var identityRefs: CFTypeRef? = nil let err = SecItemCopyMatching([ kSecClass: kSecClassIdentity, kSecMatchLimit: kSecMatchLimitAll, kSecMatchIssuers: expectedDNs, kSecReturnRef: true, ] as NSDictionary, &identityRefs) if err != errSecSuccess { completionHandler(.cancelAuthenticationChallenge, nil) return } guard let identities = identityRefs as? [SecIdentity], let identity = identities.first else { print("Identity list is empty") completionHandler(.cancelAuthenticationChallenge, nil) return } let credential = URLCredential(identity: identity, certificates: nil, persistence: .forSession) completionHandler(.useCredential, credential) } } func perform_mTLSRequest() { guard let url = URL(string: "https://sample.com/api/endpoint") else { return } var request = URLRequest(url: url) request.httpMethod = "POST" request.setValue("application/json", forHTTPHeaderField: "Accept") request.setValue("Bearer \(bearerToken)", forHTTPHeaderField: "Authorization") let delegate = KeychainCertificateDelegate() let session = URLSession(configuration: .ephemeral, delegate: delegate, delegateQueue: nil) let task = session.dataTask(with: request) { data, response, error in guard let httpResponse = response as? HTTPURLResponse, (200...299).contains(httpResponse.statusCode) else { print("Bad response") return } if let data = data { print(String(data: data, encoding: .utf8)!) } } task.resume() }
3
0
840
Sep ’25
Unexpected errSecInteractionNotAllowed (-25308) When Reading Keychain Item with kSecAttrAccessibleAfterFirstUnlock in Background
Hi everyone, I’m encountering an unexpected Keychain behavior in a production environment and would like to confirm whether this is expected or if I’m missing something. In my app, I store a deviceId in the Keychain based on the classic KeychainItemWrapper implementation. I extended it by explicitly setting: kSecAttrAccessible = kSecAttrAccessibleAfterFirstUnlock My understanding is that kSecAttrAccessibleAfterFirstUnlock should allow Keychain access while the app is running in the background, as long as the device has been unlocked at least once after reboot. However, after the app went live, I observed that when the app performs background execution (e.g., triggered by background tasks / silent push), Keychain read attempts intermittently fail with: errSecInteractionNotAllowed (-25308) This seems inconsistent with the documented behavior of kSecAttrAccessibleAfterFirstUnlock. Additional context: The issue never occurs in foreground. The issue does not appear on development devices. User devices are not freshly rebooted when this happens. The Keychain item is created successfully; only background reads fail. Setting the accessibility to kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly produces the same result. Questions: Under what circumstances can kSecAttrAccessibleAfterFirstUnlock still cause a -25308 error? Is there any known restriction when accessing Keychain while the app is running in background execution contexts? Could certain system states (Low Power Mode, Background App Refresh conditions, device lock state, etc.) cause Keychain reads to be blocked unexpectedly? Any insights or similar experiences would be greatly appreciated. Thank you!
3
0
564
3w
iPhone + Safari + Passwords violates WebAuthn spec when pubKeyCredParams doesn't contain ES256
WebAuthn Level 3 § 6.3.2 Step 2 states the authenticator must : Check if at least one of the specified combinations of PublicKeyCredentialType and cryptographic parameters in credTypesAndPubKeyAlgs is supported. If not, return an error code equivalent to "NotSupportedError" and terminate the operation. On my iPhone 15 Pro Max running iOS 18.5, Safari + Passwords does not exhibit this behavior; instead an error is not reported and an ES256 credential is created when an RP passes a non-empty sequence that does not contain {"type":"public-key","alg":-7} (e.g., [{"type":"public-key","alg":-8}]). When I use Chromium 138.0.7204.92 on my laptop running Arch Linux in conjunction with the Passwords app (connected via the "hybrid" protocol), a credential is not created and instead an error is reported per the spec.
3
0
520
Jul ’25
AES Decryption
Having trouble decrypting a string using an encryption key and an IV. var key: String var iv: String func decryptData(_ encryptedText: String) -> String? { if let textData = Data(base64Encoded: iv + encryptedText) { do { let sealedBox = try AES.GCM.SealedBox(combined: textData) let key = SymmetricKey(data: key.data(using: .utf8)!) let decryptedData = try AES.GCM.open(sealedBox, using: key) return String(data: decryptedData, encoding: .utf8) } catch { print("Decryption failed: \(error)") return nil } } return nil } Proper coding choices aside (I'm just trying anything at this point,) the main problem is opening the SealedBox. If I go to an online decryption site, I can paste in my encrypted text, the encryption key, and the IV as plain text and I can encrypt and decrypt just fine. But I can't seem to get the right combo in my Swift code. I don't have a "tag" even though I'm using the combined option. How can I make this work when all I will be receiving is the encrypted text, the encryption key, and the IV. (the encryption key is 256 bits) Try an AES site with a key of 32 digits and an IV of 16 digits and text of your choice. Use the encrypted version of the text and then the key and IV in my code and you'll see the problem. I can make the SealedBox but I can't open it to get the decrypted data. So I'm not combining the right things the right way. Anyone notice the problem?
3
0
422
Mar ’25
Invalid Persona Issue
Has anyone here encountered this? It's driving me crazy. It appears on launch. App Sandbox is enabled. The proper entitlement is selected (com.apple.security.files.user-selected.read-write) I believe this is causing an issue with app functionality for users on different machines. There is zero documentation across the internet on this problem. I am on macOS 26 beta. This error appears in both Xcode and Xcode-beta. Please help! Thank you, Logan
3
0
498
Jul ’25
Does SecTrustEvaluateWithError validates External Reference Identifiers?
Trying to validate external reference identifiers with SecTrustEvaluateWithError Method by setting reference Ids to SecPolicyCreateSSL() & SecPolicyCreateWithProperties() But two concerns are - Validates for correct reference IDs but gives error for combination of wrong & correct reference Ids 398 days validity works mandatorily before reference Ids check. Is there any other to validate external reference Ids?, which give flexibility To pass multiple combinations of reference IDs string (wrong, correct, IP, DNS) To validate reference ID without days validity of 398. Please suggest. Any help here is highly appreciated.
3
0
376
Mar ’25
Secure Enclave Cryptokit
I am using the CryptoKit SecureEnclave enum to generate Secure Enclave keys. I've got a couple of questions: What is the lifetime of these keys? When I don't store them somewhere, how does the Secure Enclave know they are gone? Do backups impact these keys? I.e. can I lose access to the key when I restore a backup? Do these keys count to the total storage capacity of the Secure Enclave? If I recall correctly, the Secure Enclave has a limited storage capacity. Do the SecureEnclave key instances count towards this storage capacity? What is the dataRepresentation and how can I use this? I'd like to store the Secure Enclave (preferably not in the Keychain due to its limitations). Is it "okay" to store this elsewhere, for instance in a file or in the UserDefaults? Can the dataRepresentation be used in other apps? If I had the capability of extracting the dataRepresentation as an attacker, could I then rebuild that key in my malicious app, as the key can be rebuilt with the Secure Enclave on the same device, or are there measures in place to prevent this (sandbox, bundle id, etc.)
3
0
244
Jun ’25
App Attest Issue in Production - Attestation Object Size Increased
Hi Apple Team and Community, We encountered a sudden and widespread failure related to the App Attest service on Friday, July 25, starting at around 9:22 AM UTC. After an extended investigation, our network engineers noted that the size of the attestation objects received from the attestKey call grew in size notably starting at that time. As a result, our firewall began blocking the requests from our app made to our servers with the Base64-encoded attestation objects in the payload, as these requests began triggering our firewall's max request length rule. Could Apple engineers please confirm whether there was any change rolled out by Apple at or around that time that would cause the attestation object size to increase? Can anyone else confirm seeing this? Any insights from Apple or others would be appreciated to ensure continued stability. Thanks!
3
0
202
Jul ’25
Migrating Sign in with Apple users for an app transfer
Dear Apple Developer Technical Support, We are currently following the official Apple documentation “TN3159: Migrating Sign in with Apple users for an app transfer” to carry out a Sign in with Apple user migration after successfully transferring several apps to a new developer account. Here is a summary of our situation: Under the original Apple developer account, we had five apps using Sign in with Apple, grouped under a shared primary app using App Grouping. Recently, we transferred three of these apps to our new Apple developer account via App Store Connect. After the transfer, these three apps are no longer associated with the original primary App ID. We reconfigured individual Services IDs for each app in the new account and enabled Sign in with Apple for each. More than 24 hours have passed since the app transfer was completed. Now we are attempting to follow the migration process to restore user access via the user.migration flow. Specifically, we are using the following script to request an Apple access token: url = "https://appleid.apple.com/auth/token" headers = {"Content-Type": "application/x-www-form-urlencoded"} data = { "grant_type": "client_credentials", "scope": "user.migration", "client_id": "com.game.friends.ios.toptop.sea", # New Services ID in the new account "client_secret": "<JWT signed with new p8 key>" } response = requests.post(url, headers=headers, data=data) However, the API response consistently returns: { "error": "invalid_client" } We have verified that the following configurations are correct: The client_secret is generated using the p8 key from the new account, signed with ES256 and correct key_id, team_id, and client_id. The client_id corresponds to the Services ID created in the new account and properly associated with the migrated app. The scope is set to user.migration. The JWT payload contains correct iss, sub, and aud values as per Apple documentation. The app has been fully transferred and reconfigured more than 24 hours ago. Problem Summary & Request for Support: According to Apple’s official documentation: “After an app is transferred, Apple updates the Sign in with Apple configuration in the background. This can take up to 24 hours. During this time, attempts to authenticate users or validate tokens may fail.” However, we are still consistently receiving invalid_client errors after the 24-hour waiting period. We suspect one of the following issues: The transferred apps may still be partially associated with the original App Grouping or primary App ID. Some Sign in with Apple configuration in Apple’s backend may not have been fully updated after the transfer. Or the Services ID is not yet fully operational for the transferred apps in the new account. We kindly request your assistance to: Verify whether the transferred apps have been completely detached from the original App Grouping and primary App ID. Confirm whether the new Services IDs under the new account are fully functional and eligible for Sign in with Apple with user.migration scope. Help identify any remaining configuration or migration issues that may cause the invalid_client error. If necessary, assist in manually ungrouping or clearing any residual App Grouping relationships affecting the new environment. We have also generated and retained the original transfer_sub identifiers and are fully prepared to complete the sub mapping once the user.migration flow becomes functional. Thank you very much for your time and support!
3
0
178
Jul ’25
Issue: Plain Executables Do Not Appear Under “Screen & System Audio Recording” on macOS 26.1 (Tahoe)
Summary I am investigating a change in macOS 26.1 (Tahoe) where plain (non-bundled) executables that request screen recording access no longer appear under: System Settings → Privacy & Security → Screen & System Audio Recording This behavior differs from macOS Sequoia, where these executables did appear in the list and could be managed through the UI. Tahoe still prompts for permission and still allows the executable to capture the screen once permission is granted, but the executable never shows up in the UI list. This breaks user expectations and removes UI-based permission management. To confirm the behavior, I created a small reproduction project with both: a plain executable, and an identical executable packaged inside an .app bundle. Only the bundled version appears in System Settings. Observed Behaviour 1. Plain Executable (from my reproduction project) When running a plain executable that captures the screen: macOS displays the normal screen-recording permission prompt. Before granting permission: screenshots show only the desktop background. After granting permission: screenshots capture the full display. The executable does not appear under “Screen & System Audio Recording”. Even when permission is granted manually (e.g., dragging the executable into the pane), the executable still does not appear, which prevents the user from modifying or revoking the permission through the UI. If the executable is launched from inside another app (e.g., VS Code, Terminal), the parent app appears in the list instead, not the executable itself. 2. Bundled App Version (from the reproduction project) I packaged the same code into a simple .app bundle (ScreenCaptureApp.app). When running the app: The same permission prompt appears. Pre-permission screenshots show the desktop background. Post-permission screenshots capture the full display. The app does appear under “Screen & System Audio Recording”. This bundle uses the same underlying executable — the only difference is packaging. Hypothesis macOS 26.1 (Tahoe) appears to require app bundles for an item to be shown in the Screen Recording privacy UI. Plain executables: still request and receive permission, still function correctly after permission is granted, but do not appear in the System Settings list. This may be an intentional change, undocumented behavior, or a regression. Reproduction Project The reproduction project includes: screen_capture.go A simple Go program that captures screenshots in a loop. screen_capture_executable Plain executable built from the Go source. ScreenCaptureApp.app/ App bundle containing the same executable. build.sh Builds both the plain executable and the app bundle. Permission reset and TCC testing scripts. The project demonstrates the behavior consistently. Steps to Reproduce Plain Executable Build: ./build.sh Reset screen capture permissions: sudo tccutil reset ScreenCapture Run: ./screen_capture_executable Before granting: screenshots show desktop only. Grant permission when prompted. After granting: full screenshots. Executable does not appear in “Screen & System Audio Recording”. Bundled App Build (if not already built): ./build.sh Reset permissions (optional): sudo tccutil reset ScreenCapture Run: open ScreenCaptureApp.app Before granting: screenshots show desktop. After granting: full screenshots. App bundle appears in the System Settings list. Additional Check I also tested launching the plain executable as a child process of another executable, similar to how some software architectures work. Result: Permission prompt appears Permission can be granted Executable still does not appear in the UI, even though TCC tracks it internally → consistent with the plain-executable behaviour. This reinforces that only app bundles are listed. Questions for Apple Is the removal of plain executables from “Screen & System Audio Recording” an intentional change in macOS Tahoe? If so, does Apple now require all screen-recording capable binaries to be packaged as .app bundles for the UI to display them? Is there a supported method for making a plain executable (launched by a parent process) appear in the list? If this is not intentional, what is the recommended path for reporting this as a regression? Files Unfortunately, I have discovered the zip file that contains my reproduction project can't be directly uploaded here. Here is a Google Drive link instead: https://drive.google.com/file/d/1sXsr3Q0g6_UzlOIL54P5wbS7yBkpMJ7A/view?usp=sharing Thank you for taking the time to review this. Any insight into whether this change is intentional or a regression would be very helpful.
3
0
912
2w
Exporting and re-importing ECC keys with file-based keychain
I'm trying to export and re-import a P-256 private key that was originally generated via SecKeyCreateRandomKey(), but I keep running into roadblocks. The key is simply exported via SecItemExport() with format formatWrappedPKCS8, and I did set a password just to be sure. Do note that I must use the file-based keychain, as the data protection keychain requires a restricted entitlement and I'm not going to pay a yearly fee just to securely store some private keys for a personal project. The 7-day limit for unsigned/self-signed binaries isn't feasible either. Here's pretty much everything I could think of trying: Simply using SecItemImport() does import the key, but I cannot set kSecAttrLabel and more importantly: kSecAttrApplicationTag. There just isn't any way to pass these attributes upfront, so it's always imported as Imported Private Key with an empty comment. Keys don't support many attributes to begin with and I need something that's unique to my program but shared across all the relevant key entries, otherwise it's impossible to query for only my program's keys. kSecAttrLabel is already used for something else and is always unique, which really only leaves kSecAttrApplicationTag. I've already accepted that this can be changed via Keychain Access, as this attribute should end up as the entry's comment. At least, that's how it works with SecKeyCreateRandomKey() and SecItemCopyMatching(). I'm trying to get that same behaviour for imports. Running SecItemUpdate() afterwards to set these 2 attributes doesn't work either, as now the kSecAttrApplicationTag is suddenly used for the entry's label instead of the comment. Even setting kSecAttrComment (just to be certain) doesn't change the comment. I think kSecAttrApplicationTag might be a creation-time attribute only, and since SecItemImport() already created a SecKey I will never be able to set this. It likely falls back to updating the label because it needs to target something that is still mutable? Using SecItemImport() with a nil keychain (i.e. create a transient key), then persisting that with SecItemAdd() via kSecValueRef does allow me to set the 2 attributes, but now the ACL is lost. Or more precise: the ACL does seem to exist as any OS prompts do show the label I originally set for the ACL, but in Keychain Access it shows as Allow all applications to access this item. I'm looking to enable Confirm before allowing access and add my own program to the Always allow access by these applications list. Private keys outright being open to all programs is of course not acceptable, and I can indeed access them from other programs without any prompts. Changing the ACL via SecKeychainItemSetAccess() after SecItemAdd() doesn't seem to do anything. It apparently succeeds but nothing changes. I also reopened Keychain Access to make sure it's not a UI "caching" issue. Creating a transient key first, then getting the raw key via SecKeyCopyExternalRepresentation() and passing that to SecItemAdd() via kSecValueData results in The specified attribute does not exist. This error only disappears if I remove almost all of the attributes. I can pass only kSecValueData, kSecClass and kSecAttrApplicationTag, but then I get The specified item already exists in the keychain errors. I found a doc that explains what determines uniqueness, so here are the rest of the attributes I'm using for SecItemAdd(): kSecClass: not mentioned as part of the primary key but still required, otherwise you'll get One or more parameters passed to a function were not valid. kSecAttrLabel: needed for my use case and not part of the primary key either, but as I said this results in The specified attribute does not exist. kSecAttrApplicationLabel: The specified attribute does not exist. As I understand it this should be the SHA1 hash of the public key, passed as Data. Just omitting it would certainly be an option if the other attributes actually worked, but right now I'm passing it to try and construct a truly unique primary key. kSecAttrApplicationTag: The specified item already exists in the keychain. kSecAttrKeySizeInBits: The specified attribute does not exist. kSecAttrEffectiveKeySize: The specified attribute does not exist. kSecAttrKeyClass: The specified attribute does not exist. kSecAttrKeyType: The specified attribute does not exist. It looks like only kSecAttrApplicationTag is accepted, but still ignored for the primary key. Even entering something that is guaranteed to be unique still results in The specified item already exists in the keychain, so I think might actually be targeting literally any key. I decided to create a completely new keychain and import it there (which does succeed), but the key is completely broken. There's no Kind and Usage at the top of Keychain Access and the table view just below it shows symmetric key instead of private. The kSecAttrApplicationTag I'm passing is still being used as the label instead of the comment and there's no ACL. I can't even delete this key because Keychain Access complains that A missing value was detected. It seems like the key doesn't really contain anything unique for its primary key, so it will always match any existing key. Using SecKeyCreateWithData() and then using that key as the kSecValueRef for SecItemAdd() results in A required entitlement isn't present. I also have to add kSecUseDataProtectionKeychain: false to SecItemAdd() (even though that should already be the default) but then I get The specified item is no longer valid. It may have been deleted from the keychain. This occurs even if I decrypt the PKCS8 manually instead of via SecItemImport(), so it's at least not like it's detecting the transient key somehow. No combination of kSecAttrIsPermanent, kSecUseDataProtectionKeychain and kSecUseKeychain on either SecKeyCreateWithData() or SecItemAdd() changes anything. I also tried PKCS12 despite that it always expects an "identity" (key + cert), while I only have (and need) a private key. Exporting as formatPKCS12 and importing it with itemTypeAggregate (or itemTypeUnknown) does import the key, and now it's only missing the kSecAttrApplicationTag as the original label is automatically included in the PKCS12. The outItems parameter contains an empty list though, which sort of makes sense because I'm not importing a full "identity". I can at least target the key by kSecAttrLabel for SecItemUpdate(), but any attempt to update the comment once again changes the label so it's not really any better than before. SecPKCS12Import() doesn't even import anything at all, even though it does return errSecSuccess while also passing kSecImportExportKeychain explicitly. Is there literally no way?
3
0
704
2w
How to Programmatically Install and Trust Root Certificate in System Keychain
I am developing a macOS application (targeting macOS 13 and later) that is non-sandboxed and needs to install and trust a root certificate by adding it to the System keychain programmatically. I’m fine with prompting the user for admin privileges or password, if needed. So far, I have attempted to execute the following command programmatically from both: A user-level process A root-level process sudo security add-trusted-cert -d -r trustRoot -k /Library/Keychains/System.keychain /path/to/cert.pem While the certificate does get installed, it does not appear as trusted in the Keychain Access app. One more point: The app is not distributed via MDM. App will be distributed out side the app store. Questions: What is the correct way to programmatically install and trust a root certificate in the System keychain? Does this require additional entitlements, signing, or profile configurations? Is it possible outside of MDM management? Any guidance or working samples would be greatly appreciated.
3
0
363
Jul ’25
macOS Gatekeeper gatekeeping text files?
I have something with a new individual on my team I've never seen before. They checked out our code repository from git and now anytime they try to open a .json file that is legitimately just a text file, GateKeeper tells them it cannot verify the integrity of this file and offers to have them throw this file away. I've seen this with binaries, and that makes sense. I removed the com.apple.quarantine extended attribute from all executable files in our source tree, but I've never seen GateKeeper prompt on text files. I could remove the extended attribute from all files in our source tree, but I fear the next time he pulls from git he'll get new ones flagged. Is there someway around this? I've never personally seen GateKeeper blocking text files.
3
1
648
Feb ’25
Need help in adding our Mac application under Remote Desktop setting from code
Our application uses Screen capture KIT API for screen recording. But from Sequoia OS, we are getting additional permission dialog which states " is requesting to bypass the system private window picker and directly access your screen and audio". It seems we need to add our app under "System settings -> Privacy & Security -> Remote Desktop" setting to avoid getting above additional dialogue in every few days. Some places mention use of .plist file that if mention in this file, the app will request for this permission. But did not seem to work or we do not understand that properly yet.
2
0
308
Feb ’25
Custom Authorization Plugin in Login Flow
What Has Been Implemented Replaced the default loginwindow:login with a custom authorization plugin. The plugin: Performs primary OTP authentication. Displays a custom password prompt. Validates the password using Open Directory (OD) APIs. Next Scenario was handling password change Password change is simulated via: sudo pwpolicy -u robo -setpolicy "newPasswordRequired=1" On next login: Plugin retrieves the old password. OD API returns kODErrorCredentialsPasswordChangeRequired. Triggers a custom change password window to collect and set new password. Issue Observed : After changing password: The user’s login keychain resets. Custom entries under the login keychain are removed. We have tried few solutions Using API, SecKeychainChangePassword(...) Using CLI, security set-keychain-password -o oldpwd -p newpwd ~/Library/Keychains/login.keychain-db These approaches appear to successfully change the keychain password, but: On launching Keychain Access, two password prompts appear, after authentication, Keychain Access window doesn't appear (no app visibility). Question: Is there a reliable way (API or CLI) to reset or update the user’s login keychain password from within the custom authorization plugin, so: The keychain is not reset or lost. Keychain Access works normally post-login. The password update experience is seamless. Thank you for your help and I appreciate your time and consideration
2
0
155
Jun ’25
Protecting XPC service when called from Authorisation Plugin
I have Authorisation Plugin which talks using XPC to my Launch Daemon to perform privileged actions. I want to protect my XPC service narrowing it to be called from known trusted clients. Now since I want authorisation plugin code which is from apple to call my service, I cannot use my own team id or app group here. I am currently banking on following properties of client connection. Apple Team ID : EQHXZ8M8AV Bundle ID starting with com.apple. Client signature verified By Apple. This is what I have come up with. func isClientTrusted(connection: NSXPCConnection) -> Bool { let clientPID = connection.processIdentifier logInfo("🔍 Checking XPC Client - PID: \(clientPID)") var secCode: SecCode? var secStaticCode: SecStaticCode? let attributes = [kSecGuestAttributePid: clientPID] as NSDictionary let status = SecCodeCopyGuestWithAttributes(nil, attributes, [], &secCode) guard status == errSecSuccess, let code = secCode else { logInfo("Failed to get SecCode for PID \(clientPID)") return false } let staticStatus = SecCodeCopyStaticCode(code, [], &secStaticCode) guard staticStatus == errSecSuccess, let staticCode = secStaticCode else { logInfo("Failed to get SecStaticCode") return false } var signingInfo: CFDictionary? let signingStatus = SecCodeCopySigningInformation(staticCode, SecCSFlags(rawValue: kSecCSSigningInformation), &signingInfo) guard signingStatus == errSecSuccess, let info = signingInfo as? [String: Any] else { logInfo("Failed to retrieve signing info") return false } // Extract and Verify Team ID if let teamID = info["teamid"] as? String { logInfo("XPC Client Team ID: \(teamID)") if teamID != "EQHXZ8M8AV" { // Apple's official Team ID logInfo("Client is NOT signed by Apple") return false } } else { logInfo("Failed to retrieve Team ID") return false } // Verify Bundle ID Starts with "com.apple." if let bundleID = info["identifier"] as? String { logInfo("XPC Client Bundle ID: \(bundleID)") if !bundleID.hasPrefix("com.apple.") { logInfo("Client is NOT an Apple system process") return false } } else { logInfo("Failed to retrieve Bundle Identifier") return false } // Verify Apple Code Signature Trust var trustRequirement: SecRequirement? let trustStatus = SecRequirementCreateWithString("anchor apple" as CFString, [], &trustRequirement) guard trustStatus == errSecSuccess, let trust = trustRequirement else { logInfo("Failed to create trust requirement") return false } let verifyStatus = SecStaticCodeCheckValidity(staticCode, [], trust) if verifyStatus != errSecSuccess { logInfo("Client's signature is NOT trusted by Apple") return false } logInfo("Client is fully verified as Apple-trusted") return true } Q: Just wanted community feedback, is this correct approach?
2
0
162
Mar ’25
iOS SMS OTP AutoFill without clicking the keyboard suggestion
Hi Apple, Currently we want to have enhancement for SMS OTP that we want to implement OTP Autofill, But after do some research we're stuck with option that the OTP only show in keyboard suggestion, is there any way for making OTP is automatically filled without user have to click the keyboard suggestion when receiving the SMS. Thanks Best Regards, Admiral Sultano Harly.
2
2
593
Nov ’25
Unable to change App Tracking configuration
I have reached out to support and they simply tell me they are unable to help me, first redirecting me to generic Apple support, after following up they provided the explanation that they only handle administrative tasks and to post on the forums. I am unable to change my App Tracking Transparency it provides no real error, though network traffic shows a 409 HTTP response from the backend API when trying to save. Here is a screenshot of the result when trying to save. Does anyone have any suggestions on how to get this resolved? I've commented back to the reviewers and they simply provided help documentation. I have a technical issue and am unable to get anyone to help resolve this.
2
0
301
Nov ’25
"My App" would like to access data from other apps pop up
Hi All, I have a finder sync extension that passes data back to my main app. It currently writes to a plist file in my group container folder. Since updating to macOS 15, I have been getting this pop-up every time I trigger this writing to the plist after the finder sync extension loads. This is how I write to the plist from my finder sync extension: let appGroupDefaults = UserDefaults(suiteName: "group.team_id.Finder-Sync-Extension-Test-Project") let items = FIFinderSyncController.default().selectedItemURLs() DispatchQueue.main.async { let url = items?.first?.absoluteString var file = items?.first?.lastPathComponent if let defaults = appGroupDefaults{ defaults.set(url, forKey: "targetURL") defaults.synchronize() } self.showWindow(with: NSExtensionContext()) } This is how I read the plist from my main app: if let defaults = UserDefaults(suiteName: "group.team_id.Finder-Sync-Extension-Test-Project") { defaults.synchronize() if let clickedUrl = defaults.string(forKey: "targetURL") { window = NSWindow(contentRect: NSScreen.main?.frame ?? .zero, styleMask: [.miniaturizable, .closable, .resizable, .titled], backing: .buffered, defer: false) window?.title = "My App" window?.makeKeyAndOrderFront(nil) textField.stringValue = clickedUrl window?.contentView?.addSubview(textField) } } It is fine if this popup happens once and the user's choice gets remembered. I just don't want it to happen every time. Any help on if this is the correct way to pass data between the finder sync extension and the main app or on how to get macOS to remember the choice of the user would be great. Thanks, James
2
0
541
Jan ’25