-
Notifications
You must be signed in to change notification settings - Fork 6k
Don't strip debug symbols by default from android builds #50443
Conversation
What about non-play store or APKs? |
In particular, what this changes in the unzipped appbundle is the inclusion of a According to the BUNDLE-METADATA description from the app bundle format,
It looks like it is up to app stores to make use of (or not make use of) the data in this directory. But this is not play store specific, it is outlined in the app bundle format.
From what I can tell they are also getting stripped by default. For an individual abi, from within the unzipped apks I don't know why this is. Listing the gradle tasks enabled, there seems to be a task 'stripReleaseDebugSymbols' that is enabled by default, which is a potential culprit. |
Thanks! I would suspect some local size differences are just due to LTO. I wasn't familiar with bundle metadata stuff, I will look into it more. This will be a great change that will help our developers with crashes and also CPU profile the engine, every supportive 👍 |
Looks like tests are failing, mostly with an error of the form
Need to figure out if there is a way to determine that "implementation-specific reason" |
…ipped does not exist lib.unstripped will not be created in a "gn --no-stripped" build See flutter#50443
This was fixed by #50629 |
It looks like this pull request may not have tests. Please make sure to add tests before merging. If you need an exemption to this rule, contact "@test-exemption-reviewer" in the #hackers channel in Chat (don't just cc them here, they won't see it! Use Discord!). If you are not sure if you need tests, consider this rule of thumb: the purpose of a test is to make sure someone doesn't accidentally revert the fix. Ask yourself, is there anything in your PR that you feel it is important we not accidentally revert back to how it was before your fix? Reviewers: Read the Tree Hygiene page and make sure this patch meets those guidelines before LGTMing. |
It seems like this is going to change the In Google3, I don't think there are any intermediate stripping steps before this file is used in APKs. Need to double check on this, will report back. |
That is correct
Please do! I've asked internally as well and mostly gotten the reply that it "should" be fine, but nothing concrete either way |
I sent cl/607168388 to perform stripping as a build action internally. The changes here seem to be universal - would this affect other platforms too? I vaguely remember that on iOS artifacts are stripped separately by luci, but not sure if we considered them in this change. |
The original PR seemed to indicate that it only affected Android. cc @jason-simmons , do you know if this is still the case? |
The I think this PR should change the build recipes for Linux desktop targets to explicitly pass |
Why do we want to strip our |
My main concern is binary size for developers building apps with the default tooling configuration. |
But why does binary size during development matter? I've never even looked at how big my APKs are during development. |
AFAICT flutter_tools does not strip the engine library when building and packaging Linux desktop apps in release mode. One option would be distributing unstripped builds of binaries like |
@@ -1063,7 +1063,7 @@ def parse_args(args): | |||
|
|||
parser.add_argument( | |||
'--stripped', | |||
default=True, | |||
default=False, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we scope this only to Android?
Right now this is applying to all builds on all platforms.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we want this for Android, we should scope this to only Android, not to all builds.
If we do this for Android, gradle will strip the libflutter.so anyway when it builds the APK by default, unless we update the build rules to tell gradle to not strip the binary.
I'm fine with having something that makes it easier to get symbols when building/debugging a Fluter app, but this change affects more platforms/workflows than I think it intends to.
I think we should be shipping unstripped binaries for all platforms and then allow our downstream users to decide to strip or not. Benefits include:
The drawbacks seem to be:
|
Another disadvantage will be increased time to install each build of an app on a device during development. This is especially noticeable on older/slower devices. I tried building a default template app with a local The APK was 173MB with the unstripped engine library and 62MB with a stripped engine. On a Moto G4, running |
This is incorrect - gradle will strip the native library during the local build process before the APK is uploaded to the store. |
Neither the original issue (flutter/flutter#60240) nor the more recent duplicate (flutter/flutter#98773) are concerning uploading APKs to the play store. They are concerning uploading appbundles to the play store (the reason that the main issue has so many likes is that the Play Store has an "Appbundle Explorer tool" which is providing this warning). Appbundles have a BUNDLE-METADATA subdirectory which contains information that is not included in the APKs that get delivered to users, but is useful to the app store itself. The debug symbols are automatically included in this directory while building an appbundle, if they are available. Comparing my branch to main, building the exact same flutter app (brand new app with only the changes from https://docs.flutter.dev/deployment/android regarding signing, and changes so the play store doesn't complain about the namespace): (Main)
(My branch)
And indeed, after uploading to the play store It simply works by default, with no Gradle changes |
I need to rebuild my debug version to verify, but I believe that APKs will continue to be stripped of symbols by default, and presumably |
Also yes I did not intend for this to affect non-android platforms. I will change the scope to fix that, though @johnmccutchan makes good points that it might be something for other platforms to consider as well |
Agreed with limiting this patch to Android. We haven't had any reports of issues on Linux so I'd prefer to avoid modifying the behaviour (or to do so only in a dedicated patch that can be discussed separately). |
Is there some other way to add the symbols to the app bundle? E.g. downloading them from cloud storage as an artifact and putting them in a place where gradle recognizes them? |
When you tried this, did you modify any Gradle files to explicitly not strip debug symbols? Or did you find that they were simply not stripped when building the same app with and without a stripped version of the engine? |
The measurement was done using local I did not modify any Gradle scripts. |
I'm not aware of any way to accomplish this short of modifying the output appbundle itself, but if anyone who comes across this knows better suggestions are welcome |
Interesting, I expect it could be possible to solve this by modifying flutter.groovy to make sure we strip the symbols by default, so we don't unintentionally increase apk install time for folks (at least in that way, hopefully the actual process of stripping is fast). I can try this and report back |
This is actually interesting because if we could make the .so.dbg files available then our own tooling could add them when we build an appbundle. I am not sure what the scope of that work would be though. |
There is an API for it as well: https://developers.google.com/android-publisher/api-ref/rest/v3/edits.deobfuscationfiles/upload |
Yes, this is what some users have been doing manually, although I believe they've been zipping files with no debug symbols in them (as they can't have the engine debug symbols, because they aren't provided in the pre-built engine artifacts), but for some reason it still makes the warning go away (ex https://stackoverflow.com/a/68778908, flutter/flutter#60240 (comment)) If we don't want to include the debug symbols in the actual engine artifacts by default and make it work as the linked step 2 indicates,
, we could alternatively grab them for release builds to put beside the appbundle, and include in our documentation where to find them and upload them to the play store. But I don't know of a way to actually make them be included in the appbundle itself as part of the build process, besides not stripping them in the first place. |
Users can definitely get the symbols today, we document how to do it at https://github.com/flutter/flutter/wiki/Crashes#get-the-symbols Including them in release builds should not regress debug build times, and should have a smaller (although still significant) impact on release size. You'll have to update a few different CI build jsons to achieve it though. Are we sure these errors are not about missing symbols for the app.so that contains the Dart code though? |
I'm going to close this to get it off review queues - it's coming up in our weekly triage and there aren't any new changes. I'm happy to talk more about what would make this something we could land (e.g. scoping it only to the build configuration for Android release, or at least just Android). I'm also still not sure why we can't have the tool distribute the symbol files we already upload, as per the crash wiki I linked last week, although if we need to make changes to how we build the "default" libflutter.so for this let's scope it to just that. |
Keeping the PR updated that we will be meeting this week to discuss next steps |
…don't strip by default on android (#161546) Remake of flutter/engine#52852. Makes it so that `stripped` defaults to false for android in `gn` arguments, i.e. we don't strip the Android engine builds. AGP does this by default when the NDK is installed (and we download it automatically now after #159756). In testing, the step that AGP does to strip symbols adds ~1-2 seconds to the build. Adds a tool verification for release app bundle builds that checks to make sure we have stripped the debug symbols and placed them in the [`BUNDLE-METADATA` directory](https://developer.android.com/guide/app-bundle/app-bundle-format). The check is done by invoking `apkanalyzer`, which takes ~`0.5` seconds, which is why the check is only enabled for release builds. BEFORE LANDING: I need to follow up on flutter/engine#50443 (comment), to ensure we start stripping symbols internally as well. ## Pre-launch Checklist - [x] I read the [Contributor Guide] and followed the process outlined there for submitting PRs. - [x] I read the [Tree Hygiene] wiki page, which explains my responsibilities. - [x] I read and followed the [Flutter Style Guide], including [Features we expect every widget to implement]. - [x] I signed the [CLA]. - [ ] I listed at least one issue that this PR fixes in the description above. - [x] I updated/added relevant documentation (doc comments with `///`). - [x] I added new tests to check the change I am making, or this PR is [test-exempt]. - [x] I followed the [breaking change policy] and added [Data Driven Fixes] where supported. - [x] All existing and new tests are passing. If you need help, consider asking for advice on the #hackers-new channel on [Discord]. <!-- Links --> [Contributor Guide]: https://github.com/flutter/flutter/blob/main/docs/contributing/Tree-hygiene.md#overview [Tree Hygiene]: https://github.com/flutter/flutter/blob/main/docs/contributing/Tree-hygiene.md [test-exempt]: https://github.com/flutter/flutter/blob/main/docs/contributing/Tree-hygiene.md#tests [Flutter Style Guide]: https://github.com/flutter/flutter/blob/main/docs/contributing/Style-guide-for-Flutter-repo.md [Features we expect every widget to implement]: https://github.com/flutter/flutter/blob/main/docs/contributing/Style-guide-for-Flutter-repo.md#features-we-expect-every-widget-to-implement [CLA]: https://cla.developers.google.com/ [flutter/tests]: https://github.com/flutter/tests [breaking change policy]: https://github.com/flutter/flutter/blob/main/docs/contributing/Tree-hygiene.md#handling-breaking-changes [Discord]: https://github.com/flutter/flutter/blob/main/docs/contributing/Chat.md [Data Driven Fixes]: https://github.com/flutter/flutter/blob/main/docs/contributing/Data-driven-Fixes.md --------- Co-authored-by: Gray Mackall <[email protected]>
See flutter/flutter#98773 (comment) and https://discord.com/channels/608014603317936148/608021010377080866/1202326905294954577. Basically, AGP strips symbols by default from the app that gets delivered to users when building app bundles, but includes them to debug crashes in
the play store(edit for clarity: in app stores). Including the symbols in the artifacts that get used to build the flutter app allows this process to work by default.See also https://support.google.com/googleplay/android-developer/answer/9848633#upload_file
WIP because (but also if any reviewer who comes across this happens to know, please tell me!) I don't actually know how these artifacts get delivered to flutter developers during the build process? Do they get downloaded? And if so where?
Also wip because the flag also changes the output directory of the build, so I need to figure out how to plumb those changes through where neededTest failures fixedPre-launch Checklist
///
).If you need help, consider asking for advice on the #hackers-new channel on Discord.