默认情况下,系统会在应用的发布 build 中剥离原生代码库。剥离过程包括移除应用使用的任何原生库中包含的符号表和调试信息。剥离原生代码库可显著缩减大小;但是,由于缺少信息(例如类和函数名称),因此无法在 Google Play 管理中心诊断崩溃问题。如需调试崩溃问题,您必须在 Play 管理中心内为应用添加调试符号文件。
上传符号文件
Google Play 管理中心会在 Android Vitals 下报告原生代码崩溃问题。只需几个步骤,即可为应用生成并上传原生代码调试符号文件。此文件可在 Android Vitals 中启用经过符号化解析的原生代码崩溃堆栈轨迹(包括类和函数名称),来帮助您在生产环境中调试应用。这些步骤因项目中使用的 Android Gradle 插件版本以及您使用的是 Android App Bundle(推荐)还是 APK 而有所不同。
android.buildTypes.release.ndk.debugSymbolLevel = { SYMBOL_TABLE | FULL }
从以下调试符号级别中进行选择:
使用 SYMBOL_TABLE 在 Play 管理中心的符号化解析后的堆栈轨迹中获取函数名称。此级别支持 Tombstone。
使用 FULL 在 Play 管理中心的符号化解析后的堆栈轨迹中获取函数名称、文件和行号。
如果您的项目构建的是 APK,请使用之前显示的 android.buildTypes.release.ndk.debugSymbolLevel 设置,以单独生成原生代码调试符号文件。手动将原生调试符号文件上传到 Google Play 管理中心(该过程类似于上传映射文件以去混淆堆栈轨迹)。在构建流程中,Android Gradle 插件会在以下项目位置输出此文件:
[null,null,["最后更新时间 (UTC):2025-07-27。"],[],[],null,["# Include native symbols in your release build\n\nBy default, native code libraries are stripped in release builds of your app.\nThis stripping consists of removing the symbol table and debugging information\ncontained in any native libraries used by your app. Stripping native code\nlibraries results in significant size savings; however, it's impossible to\ndiagnose crashes on the Google Play Console due to the missing information (such\nas class and function names). To debug crashes, you must include a debug symbols\nfile with your app in Play Console.\n\nUpload a symbols file\n---------------------\n\nThe Google Play Console reports native crashes under [Android\nvitals](/topic/performance/vitals/crash#diagnose-crashes). With a few steps, you\ncan generate and upload a native debug symbols file for your app. This file\nenables symbolicated native crash stack traces (that include class and function\nnames) in Android vitals to help you debug your app in production. These steps\nvary depending on the version of the Android Gradle plugin used in your project\nand whether you're using an Android App Bundle (recommended) or APK.\n| **Note:** To restore symbol names in crash reports yourself, use the [ndk-stack\n| tool](/ndk/guides/ndk-stack), which comes packaged with the Android NDK.\n\n### Android Gradle plugin version 4.1 or later\n\nIf your project builds an Android App Bundle (AAB), you can configure your build\nto automatically include the native debug symbols file in the AAB so it's\nuploaded to the Play Console when you publish your app. To include this file in\nrelease builds, add the following to your app's `build.gradle.kts` file:\n\n`android.buildTypes.release.ndk.debugSymbolLevel = { SYMBOL_TABLE | FULL }`\n\nSelect the debug symbol level from the following:\n\n- Use `SYMBOL_TABLE` to get function names in the Play Console's symbolicated stack traces. This level supports [tombstones](https://source.android.com/devices/tech/debug).\n- Use `FULL` to get function names, files, and line numbers in the Play Console's symbolicated stack traces.\n\n| **Note:** There is a 300 MB limit for the native debug symbols file. If your debug symbols footprint is too large, use `SYMBOL_TABLE` instead of `FULL` to decrease the file size.\n\nIf your project builds an APK, use the\n`android.buildTypes.release.ndk.debugSymbolLevel` setting shown earlier to\ngenerate the native debug symbols file separately. Manually [upload the native\ndebug symbols\nfile](https://support.google.com/googleplay/android-developer/answer/9848633#upload_file)\nto the Google Play Console (the process is similar to uploading a mapping file\nto [deobfuscate stack traces](/topic/performance/app-optimization/test-and-troubleshoot-the-optimization#recover-original-stack-trace)).\nAs part of the build process, the Android Gradle plugin outputs this file in the\nfollowing project location:\n\n`app/build/outputs/native-debug-symbols/\u003cvar\u003evariant-name\u003c/var\u003e/native-debug-symbols.zip`\n\n### Android Gradle plugin version 4.0 or earlier (and other build systems)\n\nAs part of the build process, the Android Gradle plugin keeps a copy of the\nunstripped libraries in a project directory. This directory structure is similar\nto the following: \n\n app/build/intermediates/cmake/universal/release/obj/\n ├── armeabi-v7a/\n │ ├── libgameengine.so\n │ ├── libothercode.so\n │ └── libvideocodec.so\n ├── arm64-v8a/\n │ ├── libgameengine.so\n │ ├── libothercode.so\n │ └── libvideocodec.so\n ├── x86/\n │ ├── libgameengine.so\n │ ├── libothercode.so\n │ └── libvideocodec.so\n └── x86_64/\n ├── libgameengine.so\n ├── libothercode.so\n └── libvideocodec.so\n\n| **Note:** If you use a different build system, you could modify it to store unstripped libraries in a directory with the required structure.\n\n1. Zip up the contents of this directory:\n\n cd app/build/intermediates/cmake/universal/release/obj\n zip -r symbols.zip .\n\n2. Manually [upload the `symbols.zip` file](https://support.google.com/googleplay/android-developer/answer/9848633#upload_file) to the Google Play Console.\n\n| **Note:** If your file is too big, it's likely because your `.so` files contain a symbol table and also DWARF debugging info, which isn't needed to symbolicate your code. On AGP 4.0 or lower, you can remove the DWARF debugging info by running the following command: \n|\n| `$OBJCOPY --strip-debug lib.so lib.so.sym` \n|\n| where `$OBJCOPY` points to the specific version for the ABI you're stripping (for example, `ndk-bundle/toolchains/aarch64-linux-android-4.9/prebuilt/linux-x86_64/bin/aarch64-linux-android-objcopy`). This command is equivalent to the [`SYMBOL_TABLE` option for AGP 4.1 and higher](#agp-4.1)."]]