-
Notifications
You must be signed in to change notification settings - Fork 1.7k
Description
Description
Note: I'm not sure that is a bug or something else but I asked this on StackOverflow too
I’m using Google Firebase Analytics on my React Native iOS app and I’m seeing an unexpected behavior with the first_open event and the update_with_analytics parameter.
According to the Firebase documentation, the parameter update_with_analytics is sent when Analytics is added to an app that was already installed on the device (i.e. Analytics was not present at the time of the original install and was added later).
However, my case does not match that scenario.
Important context
- The app is more than 2 years old.
- Firebase Analytics has been integrated in the app since the very first release.
- Analytics was never added later; it has always been part of the app binary.
- The iOS device is fully reset using Erase All Content and Settings.
- No iCloud backup is restored after the reset.
Observed behavior (scenario 1)
- The app already includes Firebase Analytics.
- The iOS device is fully reset.
- No iCloud backup is restored.
- The app is installed again from the App Store.
- On first launch, Firebase sends a
first_openevent where
update_with_analytics = 1.
Based on the documentation, I would expect update_with_analytics to be 0 in this case, since:
- Analytics is already present in the app binary.
- This is a clean install on a freshly reset device.
- The app was not upgraded from a non-Analytics version.
- No iCloud backup was restored.
Additional observation (scenario 2)
If, after the device reset, the app is deleted again and reinstalled once more from the App Store, then on the next first_open event:
update_with_analytics = 0
So the behavior is:
- First install after device reset →
update_with_analytics = 1 - Subsequent reinstall from the App Store →
update_with_analytics = 0
This makes the behavior even more confusing, since both installs are coming from the same App Store binary and both include Analytics.
Question
Why does Firebase Analytics send update_with_analytics = 1 on the first install after an iOS device reset, even though Analytics has always been part of the app and no iCloud backup was restored?
Is update_with_analytics actually triggered by conditions other than “Analytics was added later”, despite what the documentation suggests?
If possible, I’d appreciate clarification on what actually causes update_with_analytics to be set to 1 for first_open events on iOS, especially in device reset scenarios.
Reproducing the issue
No response
Firebase SDK Version
11.15.0
Xcode Version
16.2
Installation Method
CocoaPods
Firebase Product(s)
Analytics
Targeted Platforms
iOS
If using CocoaPods, the project's Podfile.lock
Expand Podfile.lock snippet
# Resolve react_native_pods.rb with node to allow for hoisting
require Pod::Executable.execute_command('node', ['-p',
'require.resolve(
"react-native/scripts/react_native_pods.rb",
{paths: [process.argv[1]]},
)', __dir__]).strip
$FirebaseSDKVersion = '11.15.0'
# Disable New Architecture
ENV['RCT_NEW_ARCH_ENABLED'] = '0'
ENV['USE_HERMES'] = '1'
platform :ios, '15.5'
prepare_react_native_project!
linkage = ENV['USE_FRAMEWORKS']
if linkage != nil
Pod::UI.puts "Configuring Pod with #{linkage}ally linked Frameworks".green
use_frameworks! :linkage => linkage.to_sym
end
use_frameworks! :linkage => :static
$RNFirebaseAsStaticFramework = true
project 'xxx',
'Development Debug' => :debug,
'Development Release' => :release,
'Production Debug' => :debug,
'Production Release' => :release
# Convert all permission pods into static libraries
pre_install do |installer|
Pod::Installer::Xcode::TargetValidator.send(:define_method, :verify_no_static_framework_transitive_dependencies) {}
installer.pod_targets.each do |pod|
if pod.name.eql?('RNPermissions') || pod.name.start_with?('Permission-') || pod.name.eql?('vision-camera-code-scanner') || pod.name.eql?('VisionCamera') || pod.name.eql?('RNReanimated')
def pod.build_type;
Pod::BuildType.static_library
end
end
end
end
target 'xxx' do
config = use_native_modules!
# ✅ Enable on-device conversion for Firebase Analytics
$RNFirebaseAnalyticsGoogleAppMeasurementOnDeviceConversion = true
use_react_native!(
:path => config[:reactNativePath],
# An absolute path to your application root.
:app_path => "#{Pod::Config.instance.installation_root}/.."
)
#use_flipper!({ 'Flipper' => '0.99.0' }, configurations: ['Development Debug', 'Production Debug'])
#pod 'Firebase', :modular_headers => true
#pod 'FirebaseCore', :modular_headers => true
#pod 'GoogleUtilities', :modular_headers => true
#$RNFirebaseAsStaticFramework = true
pod 'GoogleMLKit/FaceDetection', :modular_headers => true
pod 'GoogleMLKit/ImageLabeling', :modular_headers => true
post_install do |installer|
# https://github.com/facebook/react-native/blob/main/packages/react-native/scripts/react_native_pods.rb#L197-L202
react_native_post_install(
installer,
# Set `mac_catalyst_enabled` to `true` in order to apply patches
# necessary for Mac Catalyst builds
config[:reactNativePath],
:mac_catalyst_enabled => false
)
#__apply_Xcode_12_5_M1_post_install_workaround(installer)
installer.pods_project.build_configurations.each do |config|
config.build_settings["EXCLUDED_ARCHS[sdk=iphonesimulator*]"] = "arm64"
end
installer.pods_project.targets.each do |target|
if target.respond_to?(:product_type) and target.product_type == "com.apple.product-type.bundle"
target.build_configurations.each do |config|
config.build_settings['CODE_SIGNING_ALLOWED'] = 'NO'
config.build_settings['IPHONEOS_DEPLOYMENT_TARGET'] = '15.5'
end
end
end
bitcode_strip_path = `xcrun --find bitcode_strip`.chomp
def strip_bitcode_from_framework(bitcode_strip_path, framework_relative_path)
framework_path = File.join(Dir.pwd, framework_relative_path)
command = "#{bitcode_strip_path} #{framework_path} -r -o #{framework_path}"
puts "Stripping bitcode: #{command}"
system(command)
end
framework_paths = [
"Pods/OneSignalXCFramework/iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignal.xcframework/ios-arm64_armv7_armv7s/OneSignal.framework/OneSignal",
"Pods/OneSignalXCFramework/iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_armv7_armv7s/OneSignalExtension.framework/OneSignalExtension",
"Pods/OneSignalXCFramework/iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_armv7_armv7s/OneSignalCore.framework/OneSignalCore",
"Pods/OneSignalXCFramework/iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_armv7_armv7s/OneSignalOutcomes.framework/OneSignalOutcomes"
]
framework_paths.each do |framework_relative_path|
strip_bitcode_from_framework(bitcode_strip_path, framework_relative_path)
end
end
permissions_path = '../node_modules/react-native-permissions/ios'
pod 'Permission-Camera', :path => "#{permissions_path}/Camera"
pod 'Permission-PhotoLibrary', :path => "#{permissions_path}/PhotoLibrary"
end
target 'OneSignalNotificationServiceExtension' do
pod 'OneSignalXCFramework', '>= 3.0', '< 4.0'
end