Firebase Crashlytics SDK로 업그레이드

이제 새로운 공식 Firebase Crashlytics SDK를 사용하여 앱에서 Crashlytics를 설정할 수 있습니다. 이 SDK는 다른 Firebase 제품과의 일관성이 향상되었고 보다 직관적으로 사용할 수 있는 개선된 API를 제공합니다.

이 가이드에서는 기존 Fabric SDK에서 새 SDK로 업그레이드하는 방법을 설명합니다. 필요한 경우 새 API에 적용된 변경사항, 변경 사유, 코드 업데이트 방법도 설명합니다.

시작하기 전에

Firebase Crashlytics SDK는 AndroidX를 종속 항목으로 사용합니다. 앱에서 이전 버전의 앱 지원 라이브러리를 사용 중이면 먼저 앱을 AndroidX로 이전하세요.

1단계: Firebase 구성 파일 추가

  1. 프로젝트 설정을 엽니다. 내 앱 카드에서 구성 파일이 필요한 앱의 패키지 이름을 선택합니다.

  2. google-services.json 다운로드를 클릭하여 Firebase Android 구성 파일(google-services.json)을 가져옵니다.

    • 언제든지 다시 Firebase Android 구성 파일을 다운로드할 수 있습니다.

    • 구성 파일 이름에 (2)와 같은 문자가 추가되지 않았는지 확인합니다.

  3. 구성 파일을 앱의 모듈(앱 수준) 디렉터리로 이동합니다.

2단계: Firebase Crashlytics SDK 추가

  1. 앱의 루트 수준(프로젝트 수준) build.gradle에서 다음을 수행하세요.

    • Fabric의 Maven 저장소를 Google의 Maven 저장소로 바꿉니다.

    • Fabric Gradle 플러그인을 Firebase Crashlytics Gradle 플러그인으로 바꿉니다. Android 스튜디오 4.1 Canary를 사용하는 경우 Crashlytics Gradle 플러그인 버전 2.0.0 이상을 추가해야 합니다.

    buildscript {
      // ...
    
      repositories {
        // ...
    
        // Remove Fabric's Maven repository
        maven { url 'https://maven.fabric.io/public' }
    
        // Add Google's Maven repository (if it's not there already)
        google()
      }
    
      dependencies {
        // ..
    
        // Add the Google Services Gradle plugin (if it's not there already)
        classpath 'com.google.gms:google-services:4.3.10'
    
        // Remove the Fabric Gradle plugin
        classpath 'io.fabric.tools:gradle:1.31.2'
    
        // Add the Crashlytics Gradle plugin (use v2.0.0+ if you built
        // your app with Android Studio 4.1).
        classpath 'com.google.firebase:firebase-crashlytics-gradle:2.8.1'
      }
    }
    
  2. 앱 수준 build.gradle에서 Fabric 플러그인을 Firebase Crashlytics 플러그인으로 바꿉니다.

    apply plugin: 'com.android.application'
    
    // Apply the Google Services plugin (if it's not there already)
    apply plugin: 'com.google.gms.google-services'
    
    // Remove the Fabric plugin
    apply plugin: 'io.fabric'
    
    // Add the Firebase Crashlytics plugin
    apply plugin: 'com.google.firebase.crashlytics'
    
  3. 마지막으로 Firebase Crashlytics SDK를 추가합니다. 앱 수준 build.gradle에서 기존 Fabric Crashlytics SDK를 새 Firebase Crashlytics SDK로 바꿉니다. 버전 17.0.0 이상을 추가해야 합니다. 2020년 11월 15일부터는 비정상 종료 보고서가 Firebase Console에 표시되려면 이 버전 요구사항을 충족해야 합니다.

    dependencies {
      // Remove the Fabric Crashlytics SDK
      implementation 'com.crashlytics.sdk.android:crashlytics:2.10.1'
    
      // Add the Firebase Crashlytics SDK
      implementation 'com.google.firebase:firebase-crashlytics:18.2.7'
    
      // Recommended: Add the Google Analytics SDK
      implementation 'com.google.firebase:firebase-analytics:20.0.2'
    }
    

(선택사항) NDK 비정상 종료 보고 설정

Firebase Crashlytics는 Android Native Development Kit(NDK)를 사용하여 빌드한 앱의 비정상 종료 보고를 제공합니다.

네이티브 충돌을 감지하고 보고하려면 다음 안내를 따르세요.

  1. 앱 수준 build.gradle 파일에서 Fabric NDK 종속 항목을 Firebase Crashlytics NDK 종속 항목으로 바꿉니다. 그런 다음 firebaseCrashlytics 확장 프로그램을 추가하고 nativeSymbolUploadEnabled 플래그를 사용 설정해야 합니다. 이렇게 하면 앱에서 네이티브 기호를 처리하여 Crashlytics에 업로드하므로 Crashlytics 대시보드에서 올바르게 기호화된 스택 트레이스를 볼 수 있습니다.

    dependencies {
      // Remove the Fabric NDK dependency
      implementation 'com.crashlytics.sdk.android:crashlytics-ndk:2.1.1'
    
      // Add the Firebase Crashlytics NDK dependency
      implementation 'com.google.firebase:firebase-crashlytics-ndk:18.2.7'
    }
    // ...
    
    android {
        // ...
    
        buildTypes {
            release {
                /* Add the firebaseCrashlytics extension (by default,
                * it's disabled to improve build speeds) and set
                * nativeSymbolUploadEnabled to true. */
    
                firebaseCrashlytics {
                    nativeSymbolUploadEnabled true
                }
            }
        }
    }
    
    // Remove this extension (it previously enabled Crashlytics NDK reporting in Fabric)
    crashlytics {
      enableNdk true
    }
    
  2. 다음과 같이 NDK별 Gradle 태스크를 실행합니다.

    > ./gradlew app:assembleBUILD_VARIANT
    > ./gradlew app:uploadCrashlyticsSymbolFileBUILD_VARIANT
    

NDK 비정상 종료 보고에 Crashlytics를 사용하는 방법에 대한 자세한 내용은 Crashlytics NDK 문서를 참조하세요.

3단계: 코드 업데이트

다음 SDK 변경사항을 검토하고 코드를 적절하게 업데이트합니다.


이제 Crashlytics가 Firebase 설치 ID를 기반으로 ID를 순환합니다.

Crashlytics는 Crashlytics 설치 UUID를 사용하여 앱의 인스턴스를 식별하고 사용자의 데이터를 사용자 기기와 연결합니다. 이전에는 기기의 광고 ID가 변경되면 Crashlytics가 사용자의 설치 UUID를 순환했습니다. 이제는 사용자의 Firebase 설치 ID(FID)를 기반으로 설치 UUID를 순환합니다. 자세한 내용은 Firebase 설치 ID 관리를 참조하세요.

변경 사유

FID를 사용하여 다른 Firebase SDK와의 일관성을 높입니다.


Crashlytics의 새 패키지 및 클래스 이름이 com.google.firebase.crashlytics.FirebaseCrashlytics입니다.

이제 FirebaseCrashlytics 클래스의 정적 함수 대신 FirebaseCrashlytics 싱글톤에서 인스턴스 메서드를 사용하여 Crashlytics 기능을 호출할 수 있습니다. FirebaseCrashlytics 싱글톤은 getInstance() 정적 함수를 통해 전역에서 액세스할 수 있습니다.

Fabric SDK

자바

import com.crashlytics.android.Crashlytics;

// ...

// Operations on Crashlytics.
Crashlytics.someAction()

Kotlin+KTX

import com.crashlytics.android.Crashlytics

// ...

// Operations on Crashlytics.
Crashlytics.someAction()

Firebase Crashlytics SDK

자바

import com.google.firebase.crashlytics.FirebaseCrashlytics;

// ...

// Operations on FirebaseCrashlytics.
FirebaseCrashlytics crashlytics = FirebaseCrashlytics.getInstance();
crashlytics.someAction();

Kotlin+KTX

import com.google.firebase.crashlytics.FirebaseCrashlytics

// ...

// Operations on FirebaseCrashlytics.
val crashlytics = FirebaseCrashlytics.getInstance()
crashlytics.someAction()

변경 사유

이제 새 SDK의 루트 패키지와 진입점이 다른 Firebase SDK와 일치합니다. 또한 인스턴스 메서드는 정적 함수보다 모의 처리하기 쉽고 테스트 가능성 문제를 줄일 수 있습니다.


FirebaseCrashlytics가 Fabric SDK에서 더 이상 작동하지 않습니다.

이제 Crashlytics는 더 이상 Fabric API 키를 사용하지 않는 새로운 Firebase Crashlytics SDK에 정의된 ContentProvider를 사용하여 자동으로 시작됩니다. 앱의 google-services.json 파일을 사용하여 앱을 Firebase 프로젝트에 연결하고 이전 비정상 종료 데이터를 보관합니다.

AndroidManifest.xml 파일에 Fabric API 키(io.fabric.ApiKey)가 선언되었다면 삭제합니다.

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
   package="com.example.your_app_package">

   <application>
      <activity android:name=".MainActivity"/>

      <!-- Remove this line if it exists -->
      <meta-data android:name="io.fabric.ApiKey"
          android:value="xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" />

   </application>
</manifest>

기본적으로 Crashlytics는 앱의 모든 인스턴스에 대한 비정상 종료를 자동으로 수집 및 보고하지만 선택한 사용자만 사용하도록 설정할 수 있습니다. 자동 비정상 종료 보고를 사용 중지하려면 AndroidManifest.xml 파일의 <application> 블록에서 firebase_crashlytics_collection_enabledfalse로 설정합니다.

<meta-data
    android:name="firebase_crashlytics_collection_enabled"
    android:value="false" />

변경 사유

다른 Firebase SDK와 일관되도록 Crashlytics는 이제 ContentProvider를 통해 자동으로 시작됩니다. Crashlytics는 다른 SDK와 마찬가지로 자동 데이터 수집을 사용 중지하는 매니페스트 플래그를 제공하며 setCrashlyticsCollectionEnabled를 사용하여 언제든지 재정의할 수 있습니다. 이렇게 하면 앱의 비정상 종료 보고 동작을 더욱 효과적으로 제어할 수 있습니다.


Crashlytics.log가 인스턴스 메서드로 변경되었습니다.

새 SDK에는 더 이상 정적 Crashlytics.log 메서드가 포함되지 않습니다. 커스텀 로그 메시지를 추가하려면 새 인스턴스 메서드 crashlytics.log를 대신 사용하세요. 새 메서드는 더 이상 logcat에 반영되지 않습니다. 이 동작을 유지하려면 래퍼를 작성하는 것이 좋습니다. 자세한 내용은 커스텀 로그 메시지 추가를 참조하세요.

Fabric SDK

자바

Crashlytics.log("my message");

Crashlytics.log(
 Log.ERROR,
 "TAG",
 "my message");

Kotlin+KTX

Crashlytics.log("my message")

Crashlytics.log(
 Log.ERROR,
 "TAG",
 "my message")

Firebase Crashlytics SDK

자바

FirebaseCrashlytics crashlytics = FirebaseCrashlytics.getInstance();

crashlytics.log("my message");

// To log a message to a crash report, use the following syntax:
crashlytics.log("E/TAG: my message");

Kotlin+KTX

val crashlytics = FirebaseCrashlytics.getInstance()

crashlytics.log("my message")

// To log a message to a crash report, use the following syntax:
crashlytics.log("E/TAG: my message")

변경 사유

요청에 따라 logcat에 Crashlytics 로그를 출력하는 것이 중지되었습니다. 인스턴스 메서드를 사용하면 코드를 테스트하기도 더 쉽습니다.


setBool, setDouble, setFloat, setInt, setLong, setString이 setCustomKey로 집계됩니다.

커스텀 키 setter를 setCustomKey 메서드로 집계했습니다. 이전에는 커스텀 키 setter를 사용하여 비정상 종료 보고서와 함께 전송할 키-값 쌍을 설정할 수 있었습니다. 이제 기본 유형 및 문자열 유형을 수신하도록 오버로드된 setCustomKey(String, value)를 사용할 수 있습니다. 자세한 내용은 커스텀 키 추가를 참조하세요.

Fabric SDK

자바

Crashlytics.setBool("bool_key",true);

Crashlytics.setDouble("double_key",42.0);

Crashlytics.setFloat("float_key",42.0F);

Crashlytics.setInt("int_key",42);

Crashlytics.setLong("long_key",42L);

Crashlytics.setString("str_key","str_value");

Kotlin+KTX

Crashlytics.setBool("bool_key",true)

Crashlytics.setDouble("double_key",42.0)

Crashlytics.setFloat("float_key",42.0F)

Crashlytics.setInt("int_key",42)

Crashlytics.setLong("long_key",42L)

Crashlytics.setString("str_key","str_value")

Firebase Crashlytics SDK

자바

FirebaseCrashlytics crashlytics = FirebaseCrashlytics.getInstance();

crashlytics.setCustomKey("bool_key",true);

crashlytics.setCustomKey("double_key",42.0);

crashlytics.setCustomKey("float_key",42.0F);

crashlytics.setCustomKey("int_key",42);

crashlytics.setCustomKey("long_key",42L);

crashlytics.setCustomKey("str_key","42");

Kotlin+KTX

FirebaseCrashlytics crashlytics = FirebaseCrashlytics.getInstance()

crashlytics.setCustomKey("bool_key",true)

crashlytics.setCustomKey("double_key",42.0)

crashlytics.setCustomKey("float_key",42.0F)

crashlytics.setCustomKey("int_key",42)

crashlytics.setCustomKey("long_key",42L)

crashlytics.setCustomKey("str_key","42")

변경 사유

새 메서드 이름이 Crashlytics에 대해 고유하고 Crashlytics가 키-값을 준수하지 않음이 명확합니다.


setUserIdentifier가 setUserId로 변경되고 setUserName 및 setUserEmail이 삭제되었습니다.

이전에는 setUserNamesetUserEmail을 사용하여 비정상 종료와 관련된 이름이나 이메일을 설정했지만 더 이상 이러한 메서드를 정의하지 않습니다. 사용자의 ID를 설정하는 데 선호되는 새로운 방법은 setUserId를 사용하는 것입니다. 자세한 내용은 사용자 식별자 설정을 참조하세요.

Fabric SDK

자바

Crashlytics.setUserIdentifier("myAppUserId");

Crashlytics.setUserEmail("abc@example.com");

Crashlytics.setUserName("John Doe");

Kotlin+KTX

Crashlytics.setUserIdentifier("myAppUserId")

Crashlytics.setUserEmail("abc@example.com")

Crashlytics.setUserName("John Doe")

Firebase Crashlytics SDK

자바

crashlytics.setUserId("myAppUserId");

Kotlin+KTX

crashlytics.setUserId("myAppUserId")

변경 사유

다른 Firebase API와 일관되도록 메서드 이름 setUserId를 사용했고 Crashlytics를 통해 PII 로깅을 사용하지 않도록 하기 위해 setUserNamesetUserEmail을 삭제했습니다.


Crashlytics.logException(Throwable)이 FirebaseCrashlytics.recordException(Throwable)으로 대체되었습니다.

Crashlytics에서는 이제 Apple 및 Android 앱 모두에 대해 기본 제공 오류 및 예외 유형 로깅도 지원합니다.

Fabric SDK

자바

try {
/* Code that can throw checked
exceptions. */

// ...

} catch (Exception e) {
Crashlytics.logException(e);
}

Kotlin+KTX

try {
/* Code that can throw checked
exceptions. */

// ...

catch (e: Exception) {
Crashlytics.logException(e)
}

Firebase Crashlytics SDK

자바

try {
/* Code that can throw checked
exceptions. */

// ...

} catch (Exception e) {
FirebaseCrashlytics.getInstance().recordException(e);
}

Kotlin+KTX

try {
/* Code that can throw checked
exceptions. */

// ...

catch (e: Exception) {
FirebaseCrashlytics.getInstance().recordException(e)
}

변경 사유

새 메서드 recordException(Throwable)log(String)와 쉽게 구분할 수 있으며, 두 메서드의 동작 방식이 서로 다릅니다. 또한 여러 플랫폼에서 보다 일관되도록 새 API의 이름을 지정했습니다.


CrashlyticsListener가 didCrashOnPreviousExecution()으로 대체되었습니다.

이전에 CrashlyticsListener는 Crashlytics에서 이전 앱 세션이 비정상 종료로 끝나는 시점을 표시하도록 허용했습니다. 이는 재실행 시 비정상 종료 후 메시지를 표시하는 앱에 유용합니다. 이제 콜백이 동기식 API 호출 didCrashOnPreviousExecution()으로 대체됩니다.

Fabric SDK

자바

CrashlyticsListener crashlyticsListener =
new CrashlyticsListener() {
  @Override
  public void crashlyticsDidDetectCrashDuringPreviousExecution() {
    // ...App code to execute if a crash occurred during previous execution.
  }
};

CrashlyticsCore crashlyticsCore = new CrashlyticsCore.Builder()
                                      .listener(crashlyticsListener)
                                      .build();

Crashlytics crashlytics = new Crashlytics.Builder().core(crashlyticsCore).build();

Fabric.with(getContext(), crashlytics);

Kotlin+KTX

val crashlyticsListener = CrashlyticsListener {
  // ...App code to execute if a crash occurred during previous execution.
}
val crashlyticsCore = CrashlyticsCore.Builder()
  .listener(crashlyticsListener)
  .build()
val crashlytics = Crashlytics.Builder().core(crashlyticsCore).build()
Fabric.with(getContext(), crashlytics)

Firebase Crashlytics SDK

자바

if (FirebaseCrashlytics.getInstance().didCrashOnPreviousExecution()) {
// ...App code to execute if a crash occurred during previous execution.
}

Kotlin+KTX

if (FirebaseCrashlytics.getInstance().didCrashOnPreviousExecution()) {
// ...App code to execute if a crash occurred during previous execution.
}

변경 사유

새 API에는 상용구 텍스트나 콜백이 필요하지 않으므로 CrashlyticsListener로 작업할 때보다 출력 내용이 간단하고 덜 까다롭습니다. 이전에는 비동기식 콜백이 콜백 호출 시점을 보장하지 않았습니다.


비정상 종료 메서드가 삭제되었습니다.

새 SDK에는 더 이상 앱에서 강제 비정상 종료를 통해 Crashlytics 구성의 유효성을 검사하는 데 사용했었던 비정상 종료 메서드가 포함되지 않습니다. RuntimeException을 발생시켜 비정상 종료를 강제로 적용합니다.

Fabric SDK

자바

Crashlytics.getInstance().crash();

Kotlin+KTX

Crashlytics.getInstance().crash()

Firebase Crashlytics SDK

자바

throw new RuntimeException("Test Crash");

Kotlin+KTX

throw RuntimeException("Test Crash")

변경 사유

새로운 메서드는 앱의 비정상 종료가 런타임 도중 발생했는지 아니면 앱의 네이티브 SDK에서 발생했는지 명확하게 나타냅니다.


Crashlytics Gradle 플러그인에 새 플러그가 포함됩니다.

Gradle 플러그인은 계속해서 자동으로 Crashlytics 전용 Gradle 태스크를 구성하고 실행합니다. 빌드에 Crashlytics Gradle 플러그인에서의 태스크 호출이 필요한 경우 ./gradlew app:tasks를 실행하여 사용 가능한 Firebase Crashlytics 태스크를 참조하세요. 앱에서 NDK를 사용하는 경우 Crashlytics에 네이티브 기호를 계속 업로드하려면 uploadCrashlyticsSymbolFile[BUILD_VARIANT] Gradle 태스크를 명시적으로 호출해야 합니다.

Crashlytics 전용 빌드 플래그 ext.alwaysUpdateBuildIdext.enableCrashlytics는 더 이상 지원되지 않습니다. Gradle 구성이 있으면 삭제합니다. 앱에서 바이트코드 난독 처리기(예: R8 또는 Proguard)를 사용하지만 Crashlytics에 빌드의 매핑 파일을 업로드하지 않으려면 firebaseCrashlytics Gradle 확장 프로그램에 새 mappingFileUploadEnabled 플래그를 사용합니다. false로 설정하면 Crashlytics는 앱의 스택 트레이스에서 의미가 모호한 부분을 없앨 수 없습니다. 비표준 난독 처리기 구성에 mappingFile 매개변수를 사용하여 매핑 파일의 새 위치를 설정합니다. 이 플래그는 defaultConfig는 물론 모든 빌드 유형 또는 버전에 사용할 수 있습니다.

Firebase Crashlytics SDK

apply plugin: 'com.android.application'
apply plugin: 'com.google.firebase.crashlytics'
apply plugin: 'com.google.gms.google-services'

android {
    // ...

    buildTypes {
        debug {
            minifyEnabled true
            firebaseCrashlytics {
                // If you don't need crash reporting for your debug build,
                // you can speed up your build by disabling mapping file uploading.
                mappingFileUploadEnabled false
            }
        }

        release {
            minifyEnabled true
            // When minifyEnabled is set to true, Crashlytics automatically
            // uploads mapping files because the plugin detects that obfuscation
            // is enabled. mappingFileUploadEnabled defaults to true if
            // minifyEnabled is true.
        }
    }
}

변경 사유

Gradle 규칙과 보다 일관되도록 Gradle 태스크 및 구성 옵션을 업데이트했습니다.


Crashlytics는 Google 애널리틱스에서 수집한 데이터만 사용할 수 있습니다.

Firebase Crashlytics SDK로 업그레이드한 후 Fabric Answers에서 더 이상 데이터를 수집할 수 없습니다. 비정상 종료가 발생하지 않은 사용자와 탐색경로의 측정항목을 가져오려면 Google 애널리틱스를 사용하도록 전환하세요. 이전의 Answers 데이터는 Firebase로 마이그레이션할 수 없습니다.

Google 애널리틱스 시작에서 앱에 Google 애널리틱스를 추가하는 방법을 알아보세요.

변경 사유

이제 Google 애널리틱스를 통해 비정상 종료 데이터에 대한 자세한 정보를 파악할 수 있습니다. 애널리틱스를 사용하면 Firebase Console에서 앱 통계를 계속 수집할 수 있습니다.


다음 단계