Upgrade to the Firebase Crashlytics SDK

You can now set up Crashlytics in your app by using the new official Firebase Crashlytics SDK, which offers improved APIs that are more consistent with other Firebase products and more intuitive to use. This guide describes how to upgrade to the new SDK from the Fabric Crashlytics SDK. It describes the changes that come with the new APIs, the reason for the changes, and how to update your code, if required.

If your app currently uses the Fabric SDK and you want to keep it, you can set up your crash reporting right away.

Before you begin

If you haven't already, link your app from Fabric to Firebase (this guide assumes you've already migrated your app).

Step 1: Add a Firebase configuration file

  1. Open your Project Settings. In the Your apps card, select the bundle ID of the app for which you need a config file.
  2. Click Download GoogleService-Info.plist to obtain your Firebase iOS config file (GoogleService-Info.plist).

    • You can download your Firebase iOS config file again at any time.

    • Make sure the config filename is not appended with additional characters, like (2).

  3. Move your config file into the root of your Xcode project. If prompted, select to add the config file to all targets.

If you have multiple bundle IDs in your project, you must associate each bundle ID with a registered app in the Firebase console so that each app can have its own GoogleService-Info.plist file.

Step 2: Switch your pods

  1. In Cocoapods, replace the Fabric and Crashlytics pods with a Firebase/Crashlytics pod in all targets. For an optimal experience with Firebase Crashlytics, we recommend also enabling Google Analytics in your Firebase project. As part of setting up Google Analytics, add the pod for Google Analytics.

    # Add the pod for Firebase Crashlytics
    pod 'Firebase/Crashlytics'
    # Recommended: Add the Firebase pod for Google Analytics pod 'Firebase/Analytics'
  2. Directly uninstall or remove third party dependencies from Fabric, such as dependencies from Fabric Answers and third party kits.

  3. Install and update the pods, then open your .xcworkspace file to see the project in Xcode:

    pod install
    open your-project.xcworkspace

Step 3: Update your code

  1. In Xcode, rebuild your app, then re-open your .xcworkspace file again.

  2. Review the following SDK changes and make the appropriate updates to your code:


The run and upload-symbols scripts are now in FirebaseCrashlytics.

You can now access the run and upload-symbols scripts from the new FirebaseCrashlytics library. Note that you can still call upload-symbols from anywhere in your build process to manually upload your dSYMs.

In addition, Fabric’s API_KEY and BUILD_SECRET are no longer included in the new SDK. Instead, Crashlytics now uses your app’s GoogleService-info.plist to associate your app with your Firebase project and retain your historic crash data.

Fabric SDK

${PODS_ROOT}/Fabric/run API_KEY BUILD_SECRET
/path/to/pods/directory/Fabric/upload-symbols

Firebase Crashlytics SDK

${PODS_ROOT}/FirebaseCrashlytics/run
/path/to/pods/directory/FirebaseCrashlytics/upload-symbols

Reason for change

Crashlytics no longer uses the Fabric SDK as a dependency so we're moving our CLI tools to a new library.


The Crashlytics library is now called FirebaseCrashlytics.

In your app, update your import paths:

Fabric SDK

Swift

import Crashlytics

Objective-C

@import Crashlytics

Firebase Crashlytics SDK

Swift

import FirebaseCrashlytics

Objective-C

@import FirebaseCrashlytics

Reason for change

Updating the name of the Crashlytics library makes it consistent with other Firebase libraries (e.g., FirebaseFirestore and FirebaseAuth).


FirebaseCrashlytics no longer works with the Fabric SDK.

Now, FirebaseCrashlytics can only be initialized with the Firebase Crashlytics SDK. You can start up an instance of FirebaseCrashlytics by calling FirebaseApp.configure in Swift or [FIRApp configure] in Objective-C.

Within your application:didFinishLaunchingWithOptions, replace calls to Fabric.with and startWithAPIKey with a call to FirebaseApp:

Fabric SDK

Swift

Fabric.with([Crashlytics.self])

Objective-C

[Fabric with:@[[Crashlytics class]]];
+ startWithAPIKey:
+ startWithAPIKey:delegate:

Firebase Crashlytics SDK

Swift

FirebaseApp.configure()

Objective-C

[FIRApp configure]

Reason for change

Using the new methods to initialize Crashlytics is more consistent with how other Firebase services are initialized.


The crash and throwException methods are removed.

The new SDK no longer includes the crash or throwException methods. Instead, use fatalError in Swift or assert in Objective-C to force a crash.

Firebase Crashlytics SDK

Swift

// Force a test crash
fatalError()

Objective-C

// Force a test crash
assert(NO);

Reason for change

Different kinds of crashes can occur for a variety of reasons, and these methods did not clearly specify whether the resulting crashes occurred during runtime or in your app's native SDK.


The sharedInstance method is now named crashlytics.

The new SDK no longer includes the sharedInstance method. To initialize Crashlytics, use crashlytics instead (read the reference documentation for Swift or Objective-C for more information). In your app’s delegate, update your initialization script:

Fabric SDK

Swift

Crashlytics.sharedInstance()

Objective-C

[Crashlytics sharedInstance]

Firebase Crashlytics SDK

Swift

Crashlytics.crashlytics()

Objective-C

[FIRCrashlytics crashlytics]

Reason for change

We named renamed the instance getter method to be consistent with other Firebase SDKs.


Crashlytics no longer rotates IDs when the advertising ID changes.

Crashlytics now uses Instance IDs instead of advertising IDs to identify instances of your app and associate your users' data with their devices. You can use Instance IDs to help your users control their app data.

Reason for change

Using Instance IDs is consistent with other Firebase SDKs. You can now uniformly manage your Instance ID data across other Firebase services.


setUserIdentifier is now setUserID. setUserName and setUserEmail are removed.

Previously, you could set a name or email associated with a crash using setUserName and setUserEmail, but these methods will no longer be defined. The new preferred method to set IDs for your users is to use setUserID.

Fabric SDK

Swift

Crashlytics.sharedInstance().setUserIdentifier("user_id")

Crashlytics.sharedInstance().setUserEmail("user_email")

Crashlytics.sharedInstance().setUserName("user_name")

Objective-C

[[Crashlytics sharedInstance] setUserIdentifier:@"user_id"];

[[Crashlytics sharedInstance] setUserEmail:@"user_email"];

[[Crashlytics sharedInstance] setUserName:@"user_name"];

Firebase Crashlytics SDK

Swift

Crashlytics.crashlytics().setUserID("user_id")
    

Objective-C

[[FIRCrashlytics crashlytics] setUserID:@"user_id"];

Reason for change

We adopted the method name setUserID to be consistent with other Firebase APIs and removed setUserName and setUserEmail to discourage logging PII through Crashlytics.


CLSLogv and CLSNSLogv are replaced by logging functions.

The new SDK no longer includes the CLSLogv or CLSNSLogv functions. To add custom log messages, use the new logging methods in the Crashlytics library. Note that the new methods no longer print to stdout or NSLog (we recommend writing a wrapper if you want to keep this behavior).

Fabric SDK

Swift

CLSLog(@"%@, %@", first_arg, second_arg);
CLSNSLog(@"%@, %@", first_arg, second_arg);

CLSLogv(@"%@, %@", args_va_list);
CLSNSLogv(@"%@, %@", args_va_list);

CLS_LOG(@"%@, %@", first_arg, second_arg);

Objective-C

CLSLogv("%@, %@", getVaList([first_arg, second_arg]))

CLSNSLogv("%@, %@", getVaList([first_arg, second_arg]))

Firebase Crashlytics SDK

Swift

Crashlytics.crashlytics().log("\(first_arg), \(second_arg)")

Crashlytics.crashlytics().log(format: "%@, %@", arguments: getVaList([first_arg, second_arg]))

Objective-C

[[FIRCrashlytics crashlytics] log:@"first_arg, second_arg"];

[[FIRCrashlytics crashlytics] logWithFormat:@"%@, %@", first_arg, second_arg];

If you used CLS_LOG, add the following to a header file to continue getting file names and line numbers in log statements:

#define CLS_LOG(__FORMAT__, ...) [[FIRCrashlytics crashlytics] logWithFormat:@"%s line %d $ " __FORMAT__, __PRETTY_FUNCTION__, __LINE__, ##__VA_ARGS__]

Reason for change

The new methods require instances, which makes it easier to test code.


setCustomValue is replacing setObjectValue, setIntValue, setFloatValue, and setBoolValue.

The custom setter methods are no longer included in the new SDK. Previously, you could use the methods to set key/value pairs to send along with your crash report. Now, you can use setCustomValue:forKey to set key/value pairs for all data types.

Fabric SDK

Swift

Crashlytics.sharedInstance().setObjectValue("value", forKey: "object_key")

Crashlytics.sharedInstance().setIntValue(100, forKey: "int_key")

Crashlytics.sharedInstance().setFloatValue(99.9, forKey: "float_key")

Crashlytics.sharedInstance().setBoolValue(true, forKey: "bool_key")
    

Objective-C

CLSLog(@"%@, %@", first_arg, second_arg);
CLSNSLog(@"%@, %@", first_arg, second_arg);

CLSLogv(@"%@, %@", args_va_list);
CLSNSLogv(@"%@, %@", args_va_list);

CLS_LOG(@"%@, %@", first_arg, second_arg);

Firebase Crashlytics SDK

Swift

Crashlytics.crashlytics().setCustomValue("value", forKey: "object_key")

Crashlytics.crashlytics().setCustomValue(100, forKey: "int_key")

Crashlytics.crashlytics().setCustomValue(99.9, forKey: "float_key")

Crashlytics.crashlytics().setCustomValue(true, forKey: "bool_key")
    

Objective-C

[[FIRCrashlytics crashlytics] setCustomValue:@"value" forKey:@"object_key"];

[[FIRCrashlytics crashlytics] setCustomValue:@(100) forKey:@"int_key"];

[[FIRCrashlytics crashlytics] setCustomValue:@(99.9) forKey:@"float_key"];

[[FIRCrashlytics crashlytics] setCustomValue:@YES forKey:@"bool_key"];

Reason for change

The new method name is unique to Crashlytics and makes it clear that Crashlytics is not key-value compliant.


recordCustomExceptionName:reason:frameArray: is replaced by recordError.

To log custom non-fatal exceptions, use recordError instead. recordError captures the thread's call stack by calling Thread.callStackReturnAddresses() (in Swift) or [NSThread callStackReturnAddresses] (in Objective-C) instead of manually creating the frameArray.

Fabric SDK

Swift

Crashlytics.sharedInstance().recordCustomExceptionName(name, reason: reason, frameArray: [ /* frames */ ])

Objective-C

[Crashlytics sharedInstance] recordCustomExceptionName:@"exception_name"
                                                reason:@"exception_reason"
                                            frameArray:@[...]];

Firebase Crashlytics SDK

Swift

Crashlytics.crashlytics().record(error: Error)

Objective-C

[FIRCrashlytics recordError:error];

Reason for change

This function is most often used to log non-fatal exceptions. Rather than requiring you to extract the "name", "reason", and "frameArray" manually, you can now provide the instance of the exception and Crashlytics can extract the information it needs.



The CrashlyticsDelegate is replaced by separate methods for handling crash reports.

You can now use a new set of methods for handling crash reports:

  • didFinishLaunchingWithOptions is now replaced by the new handler checkForUnsentReportsWithCompletion.

  • crashlyticsDidDetectReportForLastExecution is now replaced by didCrashDuringPreviousExecution. didCrashDuringPreviousExecution allows you to conveniently detect crashes that occur during the last run of your app.

  • crashlyticsCanUseBackgroundSessions is now permanently set to true.

  • We no longer support inspecting the CLSReport object in the delegate.

By default, Crashlytics automatically uploads crash reports at startup, and you could previously call didFinishLaunchingWithOptions to let your users opt-in to crash reporting. Now, when you call setCrashlyticsCollectionEnabled=false to turn off automatic crash reporting, Crashlytics calls checkForUnsentReportsWithCompletion, which lets your users choose whether or not to send crash reports when your app crashes. You can then call sendUnsentReports if the user opts in or deleteUnsentReports if the user opts out.

Note that you can also call sendUnsentReports and deleteUnsentReports outside of checkForUnsentReportsWithCompletion. For example, you may want to permanently set up or disable crash reporting if your users have given you blanket approval or disapproval to send crash reports. Keep in mind that you may never receive crash reports if your app crashes early on in its lifecycle.

Fabric SDK

Swift

class YourClassName: CrashlyticsDelegate {

  func application(_ application: UIApplication, didFinishLaunchingWithOptions

    ...
    Crashlytics.sharedInstance().delegate = self
    ...

    return true
  }

  func crashlyticsDidDetectReport(forLastExecution report: CLSReport, completionHandler: @escaping (Bool) -> Void) {
    /* ... handle unsent reports */
  }

  func crashlyticsCanUseBackgroundSessions(_ crashlytics: Crashlytics) -> Bool {
    return true
  }
}

Objective-C

@interface YourClassName <CrashlyticsDelegate> ()
@end

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

  ...
  [[Crashlytics sharedInstance] setDelegate:self];
  ...

  return YES;
}

-(void)crashlyticsDidDetectReportForLastExecution:(CLSReport *)report completionHandler:(void (^)(BOOL submit))completionHandler {
  // ... handle unsent reports
}

-(BOOL)crashlyticsCanUseBackgroundSessions:(Crashlytics *)crashlytics {
  return YES;
}

@end

Firebase Crashlytics SDK

Swift

/* You must set setCrashlyticsCollectionEnabled to false in order to use
checkForUnsentReportsWithCompletion. */

Crashlytics.crashlytics().setCrashlyticsCollectionEnabled(false)

Crashlytics.crashlytics().checkForUnsentReports { hasUnsentReport in
  let hasUserConsent = false
  // ...get user consent.

  if hasUserConsent && hasUnsentReport {
    Crashlytics.crashlytics().sendUnsentReports()
  } else {
    Crashlytics.crashlytics().deleteUnsentReports()
  }
}

// Detect when a crash happens during your app's last run.
Crashlytics.crashlytics().didCrashDuringPreviousExecution()

Objective-C

/* You must set setCrashlyticsCollectionEnabled to false in order to use
checkForUnsentReportsWithCompletion. */

[[FIRCrashlytics crashlytics] setCrashlyticsCollectionEnabled:false];

[[FIRCrashlytics crashlytics] checkForUnsentReportsWithCompletion:^(BOOL hasUnsentReports) {
  BOOL hasConsent = false;
  // ...get consent from user.

  if (hasConsent && hasUnsentReports) {
    [[FIRCrashlytics crashlytics] sendUnsentReports];
  } else {
    [[FIRCrashlytics crashlytics] deleteUnsentReports];
  }
}];

// Detect when a crash happens during your app's last run.
if ([[FIRCrashlytics crashlytics] didCrashDuringPreviousExecution]) {
  // ...notify the user.
}

Reason for change

The new set of methods give you more control over your app's crash reporting behavior. Also, you no longer need to set up the CrashlyticsDelegate before initializing Crashlytics.


firebase_crashlytics_collection_enabled is replaced by FirebaseCrashlyticsCollectionEnabled.

When you set FirebaseCrashlyticsCollectionEnabled to false in your Info.plist, Crashlytics stops automatically sending crash reports at startup. After your app's first run, you can also disable crash reporting by setting setCrashlyticsCollectionEnabled to false in your Crashlytics.h, but note that setCrashlyticsCollectionEnabled overrides this flag.

Turn off automatic collection by replacing the firebase_crashlytics_collection_enabled key in your Info.plist:

  • Key: FirebaseCrashlyticsCollectionEnabled

  • Value: false

After the first run of your app, you can also turn off automatic collection by adding the following to your Crashlytics.h:

Firebase Crashlytics SDK

Swift

// setCrashlyticsCollectionEnabled is set to true by default.
Crashlytics.crashlytics().setCrashlyticsCollectionEnabled(false)

Objective-C

// setCrashlyticsCollectionEnabled is set to true by default.
[[FIRCrashlytics crashlytics] setCrashlyticsCollectionEnabled:false];

Reason for change

Now you have more control over how Crashlytics handles unsent crash reports when you disable automatic crash reporting. After you set FirebaseCrashlyticsCollectionEnabled to false, you can call checkForUnsentReportsWithCompletion from anywhere in your app and either send or delete unsent reports, depending on what your user chooses.


Now, Crashlytics always uses background sessions.

Previously, you could turn off background sessions if you didn't want to support it in your app by setting crashlyticsCanUseBackgroundSessions to false. Now, crashlyticsCanUseBackgroundSessions is always set to true.

Reason for change

We no longer support iOS versions below 7.0 or macOS versions below OS X 10.9, which do not support background sessions.


Crashlytics can only use data collected by Google Analytics.

Previously, when you migrated your app to Firebase Crashlytics, you kept the old Fabric SDK and could continue gathering analytics data with Fabric Answers in the Fabric dashboard. When you upgrade to the new Firebase Crashlytics SDK, you will no longer be able to collect data with Fabric Answers. Instead, you can switch over to using Google Analytics, which provides metrics for crash free users and breadcrumbs. Note that your historical Answers data cannot migrate to Firebase.

Visit Start using Google Analytics to learn how to add Google Analytics to your app. If you previously used Fabric Answers, find out how to convert your Answers events to Analytics events.

Reason for change

We now offer Google Analytics to help you get more insight into your crash data. With Analytics, you can continue gathering stats for your app in the Firebase console even after the Fabric dashboard sunsets.