react-native
react-native copied to clipboard
RN 0.62 upgrade renders huge iOS ipa build
Description
I recently upgraded from RN v0.60.5 to RN v0.62.2 and I noticed that my iOS release builds are now producing an .ipa file nearly triple in size, from ~50MB to ~130MB, however the adhoc builds increased from ~25MB to ~29MB. No other changes have been made to my app besides the upgrade, which I followed the Upgrade Helper tool for the migration. I did have one build issue with Flipper, which I was able to solve by modifying my pod file's flipper post install following these instructions. I can't seem to find any reason why my iOS build would be producing such a large release ipa file. I'm guessing it has something to do with Flipper, but that is simply a guess. I do have several existing images and fonts that I can probably be removed from my app to decrease the overall size, but regardless, why would my builds produce such a huge increase in size? I can't seem to find any reason for this. By the way, the Android build produces an release apk size fairly similar to the pre upgrade size (~49MB to ~50MB). Also to note, this is not an Expo project, but a RN Cli project.
Additionally, here is my build script that produces both an adhoc and release build:
#/bin/bash
set -e
# Try to run from the project root
if (test "${PWD%%/scripts}" != "${PWD}"); then cd ..; echo ${PWD}; fi
IOS_APP_ID=com.voyaj.ios
WORKSPACE_NAME=voyaj
IOS_SCHEME=voyaj
IOS_CONFIGURATION=Release
DEVELOPMENT_TEAM=FHKD78FHJD
echo $IOS_APP_ID
echo $WORKSPACE_NAME
echo $IOS_SCHEME
echo $IOS_CONFIGURATION
echo $IOS_EXPORT_OPTIONS_PLIST
echo "======================================"
echo "Running Pod install..."
echo "--------------------------------------"
cd ios && pod install
if [[ $? -ne 0 ]]; then
echo
echo "Pod install FAILED!"
exit 1
fi
echo
echo "======================================"
echo "Archiving the iOS project..."
echo "--------------------------------------"
xcodebuild clean archive -workspace ./${WORKSPACE_NAME}.xcworkspace -scheme $IOS_SCHEME -configuration $IOS_CONFIGURATION -derivedDataPath ./build -archivePath ./build/Products/${WORKSPACE_NAME}.xcarchive
if [[ $? -ne 0 ]]; then
echo
echo "Failed to export Adhoc IPA"
exit 1
fi
echo
echo "======================================"
echo "Exporting Adhoc IPA..."
echo "--------------------------------------"
xcodebuild -exportArchive -exportOptionsPlist "./ExportOptions/Voyaj-${DEVELOPMENT_TEAM}-AdHoc.plist" -archivePath "./build/Products/${WORKSPACE_NAME}.xcarchive" -exportPath "./build/Products/IPA/AdHoc" DEVELOPMENT_TEAM="${DEVELOPMENT_TEAM}"
if [[ $? -ne 0 ]]; then
echo
echo "Failed to export Adhoc IPA"
exit 1
fi
echo
echo "======================================"
echo "Exporting Release IPA..."
echo "--------------------------------------"
xcodebuild -exportArchive -exportOptionsPlist "./ExportOptions/Voyaj-${DEVELOPMENT_TEAM}-AppStore.plist" -archivePath "./build/Products/${WORKSPACE_NAME}.xcarchive" -exportPath "./build/Products/IPA/Release" DEVELOPMENT_TEAM="${DEVELOPMENT_TEAM}"
if [[ $? -ne 0 ]]; then
echo
echo "Failed to export Release IPA"
exit 1
fi
echo "IPA package location: ./ios/build/Products/IPA"
React Native version:
System:
OS: macOS Mojave 10.14.6
CPU: (16) x64 Intel(R) Core(TM) i9-9880H CPU @ 2.30GHz
Memory: 45.24 MB / 16.00 GB
Shell: 3.2.57 - /bin/bash
Binaries:
Node: 13.12.0 - /usr/local/bin/node
Yarn: 1.22.4 - /usr/local/bin/yarn
npm: 6.14.4 - /usr/local/bin/npm
Watchman: 4.9.0 - /usr/local/bin/watchman
Managers:
CocoaPods: 1.7.5 - /usr/local/bin/pod
SDKs:
iOS SDK:
Platforms: iOS 13.2, DriverKit 19.0, macOS 10.15, tvOS 13.2, watchOS 6.1
Android SDK:
API Levels: 28, 29
Build Tools: 28.0.3, 29.0.2
System Images: android-29 | Google APIs Intel x86 Atom, android-29 | Google Play Intel x86 Atom
Android NDK: Not Found
IDEs:
Android Studio: 3.6 AI-192.7142.36.36.6392135
Xcode: 11.3.1/11C504 - /usr/bin/xcodebuild
Languages:
Java: 1.8.0_212 - /usr/bin/javac
Python: 2.7.16 - /usr/bin/python
npmPackages:
@react-native-community/cli: Not Found
react: 16.11.0 => 16.11.0
react-native: 0.62.2 => 0.62.2
npmGlobalPackages:
*react-native*: Not Found
Steps To Reproduce
Provide a detailed list of steps that reproduce the issue.
- Upgrade existing project from 0.60.x to 0.62.2
- Modify Flipper post install block (via these instructions). My pod file's filpper post install block looks like this:
# Post Install processing for Flipper
def flipper_post_install(installer)
installer.pods_project.targets.each do |target|
if target.name == 'YogaKit'
target.build_configurations.each do |config|
config.build_settings['SWIFT_VERSION'] = '4.1'
end
end
end
file_name = Dir.glob("*.xcodeproj")[0]
app_project = Xcodeproj::Project.open(file_name)
app_project.native_targets.each do |target|
target.build_configurations.each do |config|
cflags = config.build_settings['OTHER_CFLAGS'] || '$(inherited) '
unless cflags.include? '-DFB_SONARKIT_ENABLED=1'
puts 'Adding -DFB_SONARKIT_ENABLED=1 in OTHER_CFLAGS...'
cflags << '-DFB_SONARKIT_ENABLED=1'
end
config.build_settings['OTHER_CFLAGS'] = cflags
end
app_project.save
end
installer.pods_project.save
end
Expected Results
I expect the release build ipa file size to be similar to the file size prior to upgrading to RN v0.62.2 from RN v0.60.5
Any solution or hot fix yet? I have tried commenting out all Flipper related pods and the release bundle is still way bigger than it was with 0.60.5
Hello, I tried run your command
xcodebuild clean archive -workspace ./${WORKSPACE_NAME}.xcworkspace -scheme $IOS_SCHEME -configuration $IOS_CONFIGURATION -derivedDataPath ./build -archivePath ./build/Products/${WORKSPACE_NAME}.xcarchive
with ${..} changed with my info, but I have still the issue I opened here: https://github.com/facebook/react-native/issues/28848
Do you know if this could share the same issue of yours?
@azuxx I don't think my issue is related to yours. Your issue seems to be related to an older version of node that doesn't support the spread operator. Perhaps you have multiple version of node installed? Maybe try removing all versions of node and reinstall via Homebrew. According to this ticket related to your issue, removing all versions of node and installing the latest version helped solve the issue. It also states that if you don't have nvm installed to follow these instructions, however I don't have nvm installed on my machine, only npm, so IDK. From your terminal, run $ node -v, and $ npm -v and see what versions are running on your machine. I am currently running node v13.12.0 and npm v6.14.4.
Also, are you able to build a release build via xCode's archive under the Product menu? BTW, you have to select the "Generic iOS Device" scheme to run the archive feature.
@dquessenberry thank you but I have already followed this suggestion (https://github.com/facebook/react-native/issues/28848#issuecomment-625752453) and yes I am using nvm with the latest node. I don't know what else I could try
After inspecting the contents of my release ipa and comparing pre and post v0.62.2 builds, it appears this is related to the inclusion of Swift. If I remember correctly, in order to get v0.62.2 to build, I had to create a bridging header, which may have inadvertently included the Swift framework. Does any know if Swift is required for RN v0.62.2? cc @lachtos
After inspecting the content of my release ipa and comparing pre and post v0.62.2 build, it appears this is related to the inclusion of Swift. If I remember correctly, in order to get v0.62.2 to build, I had to create a bridging header, which may have inadvertently included the Swift framework. Does any know if Swift is required for RN v0.62.2? cc @lachtos
You are right. I removed the bridging header from the project and successfully built it (all flipper related code and pods are commented out) and the build size is now back to normal.
@lachtos that's great news! I removed the bridging header and did another build, but the Swift framework is still being included. Did you do anything else beside just removing the bridging header - like did you change any build settings too?
@dquessenberry I haven't changed any build settings (I'm attaching my swift related settings in an image below). I deleted the .swift file and the bridging header, did clean and then built.
@lachtos I can't seem to locate a .swift file in my project. However, I did set the "Always Embed Swift Standard Libraries" configuration on my Project build settings, as well as my main target and test target, to No
. I cleaned the project and ran my build scripts again, and that seemed to do the trick as far as build size. However, I do get a warning during pod install that the debug and release ... target overrides the 'ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES' build setting defined in 'Pods/Target Support Files/Pods-myapp/Pods-myapp.debug.xcconfig'. This can lead to problems with the CocoaPods installation
. If I commented out the Flipper install in my podfile, the warning goes away. It seems that Flipper, or a library dependency for it, specifically YogaKit, requires Swift to be embedded in the app. So I guess for now I will comment out the Flipper install code from my pod file (although it does looks like a powerful tool) and add some comments to explain why and how to re-enable it. BTW, according to this Flipper documentation, it does looks like Flipper depends on YogaKit, which is written in Swift...
The .swift file I was talking about was the dummy file I created to trigger Xcode to create the bridging header. I think all this swift related stuff is for flipper, which I never intended to use (and I couldn't get my android builds to work with flipper) so I disabled all of it for the time being. This is also a hefty size increase for something that is not being used in production anyway. Hopefully these modifications we made don't compromise the stability of 0.62.2
I have the same issue. The size of the ipa file is way huger then it should be. It's one small project.
Same issue here
@areeb-hub #29504
Hey there, it looks like there has been no activity on this issue recently. Has the issue been fixed, or does it still require the community's attention? This issue may be closed if no further activity occurs. You may also label this issue as a "Discussion" or add it to the "Backlog" and I will leave it open. Thank you for your contributions.
I have the same issue. The size of the ipa file is way huger then it should be. It's one small project.
can you solve this??
The .swift file I was talking about was the dummy file I created to trigger Xcode to create the bridging header. I think all this swift related stuff is for flipper, which I never intended to use (and I couldn't get my android builds to work with flipper) so I disabled all of it for the time being. This is also a hefty size increase for something that is not being used in production anyway. Hopefully these modifications we made don't compromise the stability of 0.62.2
I have a package named react-native-geolocation-service it's required to add swift file and the bridging header so after deleting the package and related stuff (swift & bridging files) I got this size ( from 172 to 61 MB) 🙂
@dquessenberry there is a discussion here https://github.com/facebook/flipper/issues/1275 about not building Flipper in production. The resolution is to wrap the Flipper Pod deps with an env variable.
It is correct that the Swift file was added to allow Flipper support. But this was removed in 0.63.x I believe. https://github.com/facebook/react-native/pull/27922
Could you verify this happens in the latest RN version?
:warning: | Using Old Version |
---|---|
:information_source: | It looks like you are using an older version of React Native. Please upgrade to the latest version, and verify if the issue persists. If it does not, please let us know so we can close out this issue. This helps us ensure we are looking at issues that still exist in the current release. |
I've had the same issue (RN 0.62.2), app jumped about 100mb in size after upgrading, so after some sweat I resolved it with:
- removing
.swift
dummy (empty) file - removing generated bridging header file
- removing everything related with Flipper (from
Podfile
andAppDelegate.m
) - setting
ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES
toNO
Hope this helps someone :)
I updated from 63.4 to 64.0 and enabled Flipper and Hermes, on iOS, and the .app
size in the xcarchive went from 98mb to 650mb. Made me realize the old app size is also way too big. I haven't added any new node_modules to my project. The only change was the upgrade and the use of Flipper / Hermes. @brascene your changes reduced the size by about 150mb down to 500mb - still way too big.
I don't really see any docs on how to do release builds - it would be great to see resolution of this issue as well as updated docs to reflect the proper release build process. I build from Xcode by running Product -> Archive with a Run scheme set to Release. Does anyone have a good release build process or a link to one?
I believe the massive increase in 0.64 is due to this bug in Hermes: https://github.com/facebook/hermes/issues/499
My build size went up to 432mb, but at least once it gets into the app store it's a reasonable size.
1.Need to do bitcode enabled - Yes at Build setting tab in xcode. 2.Need to choose deployment target version above ios 13.1 Then once do clean & build and then archive. your .ipa file size will be reduce.
I tried the suggestions of @nadimahamad with iOS target 13.2 resulting in:
- reduced archive size: from 1.162 MB to 591 MB
- reduced ipa size: from 922 MB to 466 MB
- reduced hermes size: from 848 MB to 426 MB
Nevertheless ~500 MB for a framework is a lot in my opinion. But if I can trust TestFlight, the final app size on the device doesn't changed at all, it's still around 30MB.
1.Need to do bitcode enabled - Yes at Build setting tab in xcode. 2.Need to choose deployment target version above ios 13.1 Then once do clean & build and then archive. your .ipa file size will be reduce.
How can i make bitcode enabled in the project? Have to run in Jenkins
Just go to build settings in xcode and search for bitcode.
1.Need to do bitcode enabled - Yes at Build setting tab in xcode.
2.Need to choose deployment target version above ios 13.1
Then once do clean & build and then archive. your .ipa file size will be reduce.
How can i make bitcode enabled in the project? Have to run in Jenkins
Just go to build settings in xcode and search for bitcode.
Should I disable Hermes in podfile?
Hermes enabled on iOS is known to cause bigger release files.
Lol. I have managed to reduce the archive size from 1GB to 130MB. Thank you @nadimahamad
Your most welcome @rafaelmaeuer 😊 FYI: if you still want to reduce .ipa file size then you can do Hermes disable in pod file.
I want to have the improved performance from the hermes engine so thats no option for me... But today I compared archive-sizes again when reverting target back to iOS 11 (using Xcode 13.2.1 and RN 0.66.4) and voila: sizes of archives are almost equal now: 529,3 MB (iOS 13.2 target) <--> 529,6 MB (iOS 11.0 target). EDIT: After updating to RN 0.67.0 archive size is still 529,7 MB
I used the npx react-native init Test to generate an empty project 0.70.6 with Hermes with iOS Target 13.2 the size is 569MB OMG!