Touch ID本地认证触发Thread 12: EXC错误求助
Hey there, let's dig into why your Touch ID integration is causing that crash when triggering a segue—totally frustrating when things work fine until you add biometrics, right? Here are the most common culprits and how to fix them:
1. You're Running UI Operations on a Background Thread
Touch ID's evaluatePolicy callback runs on a background thread by default, but all UI actions (like segue navigation) must happen on the main thread. Calling performSegue directly in this callback violates iOS's UI thread rules and almost always triggers a crash.
Fix: Wrap Segue Logic in Main Thread Dispatch
Update your callback to switch back to the main queue before handling UI work:
func authenticateWithTouchID() { let context = LAContext() var error: NSError? if context.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: &error) { let reason = "Authenticate to access the app" context.evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: reason) { [weak self] success, error in // Force UI operations onto the main thread DispatchQueue.main.async { guard let self = self else { return } if success { // Make sure this identifier matches your Storyboard segue exactly self.performSegue(withIdentifier: "YourTargetSegueID", sender: self) } else { print("Authentication failed: \(error?.localizedDescription ?? "Unknown error")") } } } } else { print("Touch ID unavailable: \(error?.localizedDescription ?? "Unknown issue")") } }
2. Invalid or Nil Segue Identifier
Even if your segue works without Touch ID, it's easy to mistype the identifier in the Touch ID callback, or have a variable holding the identifier become nil by the time the callback fires.
Fix: Double-Check Segue Configuration
- Open your Storyboard, select the segue, and confirm its Identifier matches exactly what you're passing to
performSegue(Swift is case-sensitive!). - If you're using a variable for the identifier, ensure it's properly initialized and not nil when the callback runs.
3. View Controller Was Deallocated Before Callback Fires
If the user navigates away from your view controller while Touch ID is being verified, the callback might fire when self is already deallocated. This causes an EXC_BAD_ACCESS error when you try to call performSegue on a dangling reference.
Fix: Use Weak Self to Avoid Dangling References
Add [weak self] to your callback closure and safely unwrap it before performing any actions:
context.evaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, localizedReason: reason) { [weak self] success, error in DispatchQueue.main.async { // Safely check if the view controller still exists guard let strongSelf = self else { print("View controller no longer exists—aborting segue") return } if success { strongSelf.performSegue(withIdentifier: "YourTargetSegueID", sender: strongSelf) } } }
Extra Troubleshooting Tips
- Inspect the Crash Log: Look at the exact EXC error type (e.g., EXC_BAD_ACCESS vs. EXC_BREAKPOINT) and call stack in Xcode. This will pinpoint exactly where the crash occurs.
- Test with a Simple UI Action: Replace the segue call with a
UIAlertControllerfirst. If the alert shows up without crashing, the issue is definitely tied to segue execution (either thread or identifier problem). - Verify Permissions: Ensure your app has the correct biometric permissions in
Info.plist(though this usually causes auth failures, not crashes).
内容的提问来源于stack exchange,提问作者Arnav GUPTA

