@dreamhorizonorg/pulse-react-native 0.0.1 → 0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (135) hide show
  1. package/PulseReactNativeOtel.podspec +1 -1
  2. package/README.md +34 -879
  3. package/android/build.gradle +10 -15
  4. package/android/proguard-rules.pro +3 -99
  5. package/android/src/main/java/com/pulsereactnativeotel/Pulse.kt +87 -0
  6. package/android/src/main/java/com/pulsereactnativeotel/PulseOtelConstants.kt +1 -1
  7. package/android/src/main/java/com/pulsereactnativeotel/PulseReactNativeOtelLogger.kt +3 -1
  8. package/android/src/main/java/com/pulsereactnativeotel/PulseReactNativeOtelModule.kt +53 -3
  9. package/android/src/main/java/com/pulsereactnativeotel/PulseReactNativeOtelPackage.kt +1 -1
  10. package/android/src/main/java/com/pulsereactnativeotel/PulseReactNativeOtelTracer.kt +24 -8
  11. package/android/src/main/java/com/pulsereactnativeotel/ReactNativeScreenAttributesLogRecordProcessor.kt +21 -0
  12. package/android/src/main/java/com/pulsereactnativeotel/ReactNativeScreenAttributesSpanProcessor.kt +30 -0
  13. package/android/src/main/java/com/pulsereactnativeotel/ReactNativeScreenNameTracker.kt +17 -0
  14. package/app.plugin.js +1 -0
  15. package/ios/PulseReactNativeOtel.mm +7 -1
  16. package/lib/module/NativePulseReactNativeOtel.js.map +1 -1
  17. package/lib/module/config.js +29 -9
  18. package/lib/module/config.js.map +1 -1
  19. package/lib/module/errorBoundary.js.map +1 -1
  20. package/lib/module/events.js +6 -0
  21. package/lib/module/events.js.map +1 -1
  22. package/lib/module/index.js +4 -2
  23. package/lib/module/index.js.map +1 -1
  24. package/lib/module/navigation/index.js +172 -0
  25. package/lib/module/navigation/index.js.map +1 -0
  26. package/lib/module/navigation/navigation.interface.js +2 -0
  27. package/lib/module/navigation/navigation.interface.js.map +1 -0
  28. package/lib/module/navigation/screen-interactive.js +101 -0
  29. package/lib/module/navigation/screen-interactive.js.map +1 -0
  30. package/lib/module/navigation/screen-load.js +68 -0
  31. package/lib/module/navigation/screen-load.js.map +1 -0
  32. package/lib/module/navigation/screen-session.js +60 -0
  33. package/lib/module/navigation/screen-session.js.map +1 -0
  34. package/lib/module/navigation/useNavigationTracking.js +33 -0
  35. package/lib/module/navigation/useNavigationTracking.js.map +1 -0
  36. package/lib/module/navigation/utils.js +17 -0
  37. package/lib/module/navigation/utils.js.map +1 -0
  38. package/lib/module/network-interceptor/graphql-helper.js +92 -0
  39. package/lib/module/network-interceptor/graphql-helper.js.map +1 -0
  40. package/lib/module/network-interceptor/request-tracker-xhr.js +2 -1
  41. package/lib/module/network-interceptor/request-tracker-xhr.js.map +1 -1
  42. package/lib/module/network-interceptor/span-helpers.js +24 -16
  43. package/lib/module/network-interceptor/span-helpers.js.map +1 -1
  44. package/lib/module/network-interceptor/url-helper.js +58 -2
  45. package/lib/module/network-interceptor/url-helper.js.map +1 -1
  46. package/lib/module/pulse.constants.js +42 -0
  47. package/lib/module/pulse.constants.js.map +1 -0
  48. package/lib/module/trace.js +17 -2
  49. package/lib/module/trace.js.map +1 -1
  50. package/lib/typescript/plugin/src/index.d.ts +5 -0
  51. package/lib/typescript/plugin/src/index.d.ts.map +1 -0
  52. package/lib/typescript/plugin/src/types.d.ts +27 -0
  53. package/lib/typescript/plugin/src/types.d.ts.map +1 -0
  54. package/lib/typescript/plugin/src/utils.d.ts +10 -0
  55. package/lib/typescript/plugin/src/utils.d.ts.map +1 -0
  56. package/lib/typescript/plugin/src/withAndroidPulse.d.ts +4 -0
  57. package/lib/typescript/plugin/src/withAndroidPulse.d.ts.map +1 -0
  58. package/lib/typescript/src/NativePulseReactNativeOtel.d.ts +8 -2
  59. package/lib/typescript/src/NativePulseReactNativeOtel.d.ts.map +1 -1
  60. package/lib/typescript/src/config.d.ts +8 -2
  61. package/lib/typescript/src/config.d.ts.map +1 -1
  62. package/lib/typescript/src/errorBoundary.d.ts.map +1 -1
  63. package/lib/typescript/src/events.d.ts.map +1 -1
  64. package/lib/typescript/src/index.d.ts +5 -3
  65. package/lib/typescript/src/index.d.ts.map +1 -1
  66. package/lib/typescript/src/navigation/index.d.ts +12 -0
  67. package/lib/typescript/src/navigation/index.d.ts.map +1 -0
  68. package/lib/typescript/src/navigation/navigation.interface.d.ts +17 -0
  69. package/lib/typescript/src/navigation/navigation.interface.d.ts.map +1 -0
  70. package/lib/typescript/src/navigation/screen-interactive.d.ts +16 -0
  71. package/lib/typescript/src/navigation/screen-interactive.d.ts.map +1 -0
  72. package/lib/typescript/src/navigation/screen-load.d.ts +13 -0
  73. package/lib/typescript/src/navigation/screen-load.d.ts.map +1 -0
  74. package/lib/typescript/src/navigation/screen-session.d.ts +15 -0
  75. package/lib/typescript/src/navigation/screen-session.d.ts.map +1 -0
  76. package/lib/typescript/src/navigation/useNavigationTracking.d.ts +5 -0
  77. package/lib/typescript/src/navigation/useNavigationTracking.d.ts.map +1 -0
  78. package/lib/typescript/src/navigation/utils.d.ts +8 -0
  79. package/lib/typescript/src/navigation/utils.d.ts.map +1 -0
  80. package/lib/typescript/src/network-interceptor/graphql-helper.d.ts +8 -0
  81. package/lib/typescript/src/network-interceptor/graphql-helper.d.ts.map +1 -0
  82. package/lib/typescript/src/network-interceptor/request-tracker-xhr.d.ts.map +1 -1
  83. package/lib/typescript/src/network-interceptor/span-helpers.d.ts +1 -1
  84. package/lib/typescript/src/network-interceptor/span-helpers.d.ts.map +1 -1
  85. package/lib/typescript/src/network-interceptor/url-helper.d.ts +9 -0
  86. package/lib/typescript/src/network-interceptor/url-helper.d.ts.map +1 -1
  87. package/lib/typescript/src/pulse.constants.d.ts +35 -0
  88. package/lib/typescript/src/pulse.constants.d.ts.map +1 -0
  89. package/lib/typescript/src/pulse.interface.d.ts +2 -1
  90. package/lib/typescript/src/pulse.interface.d.ts.map +1 -1
  91. package/lib/typescript/src/trace.d.ts +7 -0
  92. package/lib/typescript/src/trace.d.ts.map +1 -1
  93. package/package.json +29 -9
  94. package/plugin/build/index.d.ts +4 -0
  95. package/plugin/build/index.js +10 -0
  96. package/plugin/build/types.d.ts +26 -0
  97. package/plugin/build/types.js +2 -0
  98. package/plugin/build/utils.d.ts +9 -0
  99. package/plugin/build/utils.js +102 -0
  100. package/plugin/build/withAndroidPulse.d.ts +3 -0
  101. package/plugin/build/withAndroidPulse.js +53 -0
  102. package/scripts/pulse-cli.js +82 -0
  103. package/scripts/uploadService.js +122 -0
  104. package/scripts/utils.js +125 -0
  105. package/src/NativePulseReactNativeOtel.ts +11 -2
  106. package/src/config.ts +37 -8
  107. package/src/errorBoundary.tsx +11 -5
  108. package/src/events.ts +7 -0
  109. package/src/global.d.ts +0 -1
  110. package/src/index.tsx +6 -3
  111. package/src/navigation/index.ts +306 -0
  112. package/src/navigation/navigation.interface.ts +19 -0
  113. package/src/navigation/screen-interactive.ts +149 -0
  114. package/src/navigation/screen-load.ts +103 -0
  115. package/src/navigation/screen-session.ts +87 -0
  116. package/src/navigation/useNavigationTracking.ts +50 -0
  117. package/src/navigation/utils.ts +19 -0
  118. package/src/network-interceptor/graphql-helper.ts +110 -0
  119. package/src/network-interceptor/request-tracker-xhr.ts +3 -1
  120. package/src/network-interceptor/span-helpers.ts +27 -18
  121. package/src/network-interceptor/url-helper.ts +67 -1
  122. package/src/pulse.constants.ts +38 -0
  123. package/src/pulse.interface.ts +6 -1
  124. package/src/trace.ts +25 -2
  125. package/LICENSE +0 -20
  126. package/lib/module/network-interceptor/request-tracker-fetch.js +0 -72
  127. package/lib/module/network-interceptor/request-tracker-fetch.js.map +0 -1
  128. package/lib/module/reactNavigation.js +0 -100
  129. package/lib/module/reactNavigation.js.map +0 -1
  130. package/lib/typescript/src/network-interceptor/request-tracker-fetch.d.ts +0 -7
  131. package/lib/typescript/src/network-interceptor/request-tracker-fetch.d.ts.map +0 -1
  132. package/lib/typescript/src/reactNavigation.d.ts +0 -10
  133. package/lib/typescript/src/reactNavigation.d.ts.map +0 -1
  134. package/src/network-interceptor/request-tracker-fetch.ts +0 -96
  135. package/src/reactNavigation.tsx +0 -146
@@ -68,30 +68,25 @@ android {
68
68
  }
69
69
  }
70
70
 
71
+ kotlin {
72
+ explicitApi()
73
+ }
74
+
71
75
  repositories {
72
76
  mavenCentral()
73
77
  google()
74
78
  }
75
79
 
76
- def kotlin_version = getExtOrDefault("kotlinVersion")
77
-
80
+ def pulse_version = "0.0.2-alpha"
78
81
  dependencies {
79
82
  implementation("com.facebook.react:react-android")
80
- implementation("org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version")
81
83
 
82
- api("org.dreamhorizon:pulse-android-sdk:0.0.1-alpha") {
84
+ api("org.dreamhorizon:pulse-android-sdk:$pulse_version") {
83
85
  exclude group: "com.squareup.okhttp3", module: "okhttp-jvm"
84
86
  }
87
+ implementation("org.dreamhorizon:pulse-semconv:$pulse_version")
88
+ implementation("org.dreamhorizon:pulse-sampling-models:$pulse_version")
85
89
  api("com.squareup.okhttp3:okhttp:5.0.0-alpha.14")
86
- }
87
-
88
- configurations.all {
89
- resolutionStrategy {
90
- eachDependency {
91
- if (requested.group == "com.squareup.okhttp3" && requested.name == "okhttp-jvm") {
92
- useTarget("com.squareup.okhttp3:okhttp:${requested.version}")
93
- because("Resolving okhttp-jvm to okhttp for Android compatibility")
94
- }
95
- }
96
- }
90
+ implementation("io.opentelemetry:opentelemetry-sdk")
91
+ implementation("org.jetbrains.kotlinx:kotlinx-serialization-json:1.8.0")
97
92
  }
@@ -1,49 +1,7 @@
1
1
  # Pulse React Native OpenTelemetry - Consumer ProGuard Rules
2
2
  # These rules are automatically applied to consuming applications
3
-
4
- # ===== OpenTelemetry ProGuard Rules =====
5
- # OpenTelemetry is heavily reflection-based and needs these classes preserved
6
-
7
- # Keep all OpenTelemetry classes
8
- -keep class io.opentelemetry.** { *; }
9
- -dontwarn io.opentelemetry.**
10
-
11
- # Keep OpenTelemetry API
12
- -keep class io.opentelemetry.api.** { *; }
13
- -keep interface io.opentelemetry.api.** { *; }
14
-
15
- # Keep OpenTelemetry SDK
16
- -keep class io.opentelemetry.sdk.** { *; }
17
-
18
- # Keep OpenTelemetry Context (critical for span propagation)
19
- -keep class io.opentelemetry.context.** { *; }
20
- -keep class io.opentelemetry.context.Context { *; }
21
- -keep class io.opentelemetry.context.Scope { *; }
22
- -keep class io.opentelemetry.context.ImplicitContextKeyed { *; }
23
- -keep interface io.opentelemetry.context.** { *; }
24
-
25
- # ===== Missing Compile-Time Annotations =====
26
- # These annotations are compile-time only and not needed at runtime
27
- # R8/ProGuard should ignore them when missing
28
-
29
- -dontwarn com.google.errorprone.annotations.**
30
- -dontwarn javax.annotation.**
31
- -dontwarn org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement
32
- -dontwarn edu.umd.cs.findbugs.annotations.**
33
- -dontwarn org.checkerframework.checker.**
34
- -dontwarn com.google.j2objc.annotations.**
35
-
36
- # Specifically ignore the MustBeClosed annotation that R8 complains about
37
- -dontwarn com.google.errorprone.annotations.MustBeClosed
38
- -dontwarn com.google.errorprone.annotations.CanIgnoreReturnValue
39
- -dontwarn com.google.errorprone.annotations.CheckReturnValue
40
- -dontwarn com.google.errorprone.annotations.concurrent.**
41
-
42
- # ===== Missing Java SE Classes (not available in Android) =====
43
- # java.beans package is part of Java SE but not Android
44
- # These are referenced by libraries like SnakeYAML and Jackson but not used at runtime
45
-
46
- -dontwarn java.beans.**
3
+ -dontwarn io.grpc.Drainable
4
+ -dontwarn io.grpc.KnownLength
47
5
  -dontwarn java.beans.BeanInfo
48
6
  -dontwarn java.beans.ConstructorProperties
49
7
  -dontwarn java.beans.FeatureDescriptor
@@ -51,58 +9,4 @@
51
9
  -dontwarn java.beans.Introspector
52
10
  -dontwarn java.beans.PropertyDescriptor
53
11
  -dontwarn java.beans.Transient
54
-
55
- # SnakeYAML uses java.beans for reflection but has fallbacks
56
- -dontwarn org.yaml.snakeyaml.introspector.MethodProperty
57
-
58
- # Jackson uses java.beans for annotations but has fallbacks
59
- -dontwarn com.fasterxml.jackson.databind.ext.Java7SupportImpl
60
-
61
- # ===== Pulse React Native OTEL =====
62
- # Keep our library classes
63
- -keep class com.pulsereactnativeotel.** { *; }
64
- -keepclassmembers class com.pulsereactnativeotel.** { *; }
65
-
66
- # Keep Kotlin metadata
67
- -keep class kotlin.Metadata { *; }
68
-
69
- # ===== General Rules =====
70
- # Keep attributes needed for proper functioning
71
- -keepattributes Signature
72
- -keepattributes *Annotation*
73
- -keepattributes InnerClasses
74
- -keepattributes EnclosingMethod
75
- -keepattributes Exceptions
76
- -keepattributes SourceFile
77
- -keepattributes LineNumberTable
78
-
79
- # Keep generic signatures for proper type checking
80
- -keepattributes Signature
81
-
82
- # ===== React Native Specific =====
83
- # Keep native method names
84
- -keepclasseswithmembernames class * {
85
- native <methods>;
86
- }
87
-
88
- # Keep React Native annotations
89
- -keep,allowobfuscation @interface com.facebook.proguard.annotations.DoNotStrip
90
- -keep,allowobfuscation @interface com.facebook.proguard.annotations.KeepGettersAndSetters
91
- -keep,allowobfuscation @interface com.facebook.common.internal.DoNotStrip
92
- -keep,allowobfuscation @interface com.facebook.jni.annotations.DoNotStrip
93
-
94
- -keep @com.facebook.proguard.annotations.DoNotStrip class *
95
- -keep @com.facebook.common.internal.DoNotStrip class *
96
- -keep @com.facebook.jni.annotations.DoNotStrip class *
97
-
98
- -keepclassmembers class * {
99
- @com.facebook.proguard.annotations.DoNotStrip *;
100
- @com.facebook.common.internal.DoNotStrip *;
101
- @com.facebook.jni.annotations.DoNotStrip *;
102
- }
103
-
104
- -keepclassmembers @com.facebook.proguard.annotations.KeepGettersAndSetters class * {
105
- void set*(***);
106
- *** get*();
107
- }
108
-
12
+ -dontwarn org.osgi.annotation.bundle.Export
@@ -0,0 +1,87 @@
1
+ @file:OptIn(io.opentelemetry.android.Incubating::class)
2
+
3
+ package com.pulsereactnativeotel
4
+
5
+ import android.app.Application
6
+ import com.pulse.android.sdk.PulseSDK
7
+ import com.pulse.semconv.PulseAttributes
8
+ import io.opentelemetry.android.agent.connectivity.EndpointConnectivity
9
+ import io.opentelemetry.android.agent.dsl.DiskBufferingConfigurationSpec
10
+ import io.opentelemetry.android.agent.dsl.instrumentation.InstrumentationConfiguration
11
+ import io.opentelemetry.android.agent.session.SessionConfig
12
+ import io.opentelemetry.api.common.Attributes
13
+ import io.opentelemetry.sdk.logs.SdkLoggerProviderBuilder
14
+ import io.opentelemetry.sdk.resources.ResourceBuilder
15
+ import io.opentelemetry.sdk.trace.SdkTracerProviderBuilder
16
+ import java.util.function.BiFunction
17
+
18
+ /**
19
+ * React Native wrapper for PulseSDK that automatically adds React Native screen name processors.
20
+ * This ensures React Native screen names override Android Activity/Fragment names in telemetry.
21
+ */
22
+ public object Pulse : PulseSDK by PulseSDK.INSTANCE {
23
+ public override fun initialize(
24
+ application: Application,
25
+ endpointBaseUrl: String,
26
+ endpointHeaders: Map<String, String>,
27
+ spanEndpointConnectivity: EndpointConnectivity,
28
+ logEndpointConnectivity: EndpointConnectivity,
29
+ metricEndpointConnectivity: EndpointConnectivity,
30
+ resource: (ResourceBuilder.() -> Unit)?,
31
+ sessionConfig: SessionConfig,
32
+ globalAttributes: (() -> Attributes)?,
33
+ diskBuffering: (DiskBufferingConfigurationSpec.() -> Unit)?,
34
+ tracerProviderCustomizer: BiFunction<SdkTracerProviderBuilder, Application, SdkTracerProviderBuilder>?,
35
+ loggerProviderCustomizer: BiFunction<SdkLoggerProviderBuilder, Application, SdkLoggerProviderBuilder>?,
36
+ instrumentations: (InstrumentationConfiguration.() -> Unit)?,
37
+ ) {
38
+ val rnTracerProviderCustomizer = BiFunction<SdkTracerProviderBuilder, Application, SdkTracerProviderBuilder> { tracerProviderBuilder, _ ->
39
+ tracerProviderBuilder.addSpanProcessor(ReactNativeScreenAttributesSpanProcessor())
40
+ }
41
+
42
+ val rnLoggerProviderCustomizer = BiFunction<SdkLoggerProviderBuilder, Application, SdkLoggerProviderBuilder> { loggerProviderBuilder, _ ->
43
+ loggerProviderBuilder.addLogRecordProcessor(ReactNativeScreenAttributesLogRecordProcessor())
44
+ }
45
+
46
+ val mergedTracerProviderCustomizer = if (tracerProviderCustomizer != null) {
47
+ BiFunction<SdkTracerProviderBuilder, Application, SdkTracerProviderBuilder> { tracerProviderBuilder, application ->
48
+ val builderWithRn = rnTracerProviderCustomizer.apply(tracerProviderBuilder, application)
49
+ tracerProviderCustomizer.apply(builderWithRn, application)
50
+ }
51
+ } else {
52
+ rnTracerProviderCustomizer
53
+ }
54
+
55
+ val mergedLoggerProviderCustomizer = if (loggerProviderCustomizer != null) {
56
+ BiFunction<SdkLoggerProviderBuilder, Application, SdkLoggerProviderBuilder> { loggerProviderBuilder, application ->
57
+ val builderWithRn = rnLoggerProviderCustomizer.apply(loggerProviderBuilder, application)
58
+ loggerProviderCustomizer.apply(builderWithRn, application)
59
+ }
60
+ } else {
61
+ rnLoggerProviderCustomizer
62
+ }
63
+
64
+ // Set telemetry.sdk.name for React Native SDK (read in OpenTelemetryRumInitializer for sampling)
65
+ val rnResource: (ResourceBuilder.() -> Unit) = {
66
+ put(PulseAttributes.TELEMETRY_SDK_NAME_KEY, PulseAttributes.PulseSdkNames.ANDROID_RN)
67
+ resource?.invoke(this)
68
+ }
69
+
70
+ PulseSDK.INSTANCE.initialize(
71
+ application = application,
72
+ endpointBaseUrl = endpointBaseUrl,
73
+ endpointHeaders = endpointHeaders,
74
+ spanEndpointConnectivity = spanEndpointConnectivity,
75
+ logEndpointConnectivity = logEndpointConnectivity,
76
+ metricEndpointConnectivity = metricEndpointConnectivity,
77
+ resource = rnResource,
78
+ sessionConfig = sessionConfig,
79
+ globalAttributes = globalAttributes,
80
+ diskBuffering = diskBuffering,
81
+ tracerProviderCustomizer = mergedTracerProviderCustomizer,
82
+ loggerProviderCustomizer = mergedLoggerProviderCustomizer,
83
+ instrumentations = instrumentations,
84
+ )
85
+ }
86
+ }
87
+
@@ -1,6 +1,6 @@
1
1
  package com.pulsereactnativeotel
2
2
 
3
- object PulseOtelConstants {
3
+ internal object PulseOtelConstants {
4
4
  const val INSTRUMENTATION_SCOPE = "com.pulsereactnativeotel"
5
5
 
6
6
  const val ATTR_ERROR_FATAL = "error.fatal"
@@ -4,8 +4,9 @@ import com.facebook.react.bridge.ReadableArray
4
4
  import com.facebook.react.bridge.ReadableMap
5
5
  import com.facebook.react.bridge.ReadableType
6
6
  import com.pulse.android.sdk.PulseSDK
7
+ import com.pulse.semconv.PulseAttributes
7
8
 
8
- object PulseReactNativeOtelLogger {
9
+ internal object PulseReactNativeOtelLogger {
9
10
 
10
11
  fun trackEvent(
11
12
  event: String,
@@ -35,6 +36,7 @@ object PulseReactNativeOtelLogger {
35
36
  put(PulseOtelConstants.ATTR_THREAD_ID, getCurrentThreadId())
36
37
  put(PulseOtelConstants.ATTR_THREAD_NAME, Thread.currentThread().name)
37
38
  put(PulseOtelConstants.ATTR_ERROR_SOURCE, PulseOtelConstants.ERROR_SOURCE_JS)
39
+ put(PulseAttributes.PULSE_TYPE.key, if (isFatal) PulseAttributes.PulseTypeValues.CRASH else PulseAttributes.PulseTypeValues.NON_FATAL)
38
40
  attributes?.let { putAll(it.toMap()) }
39
41
  }
40
42
 
@@ -1,15 +1,22 @@
1
1
  package com.pulsereactnativeotel
2
2
 
3
+ import com.facebook.react.bridge.Arguments
3
4
  import com.facebook.react.bridge.ReactApplicationContext
4
5
  import com.facebook.react.bridge.ReadableMap
6
+ import com.facebook.react.bridge.WritableMap
5
7
  import com.facebook.react.module.annotations.ReactModule
6
8
  import com.pulse.android.sdk.PulseSDK
9
+ import android.content.Context
7
10
  import android.os.Looper
8
11
  import android.util.Log
9
12
  import android.os.Handler
13
+ import com.pulse.sampling.models.PulseSdkConfig
14
+ import com.pulse.sampling.models.PulseSdkName
15
+ import com.pulse.sampling.models.PulseFeatureName
16
+ import kotlinx.serialization.json.Json
10
17
 
11
18
  @ReactModule(name = PulseReactNativeOtelModule.NAME)
12
- class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
19
+ internal class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
13
20
  NativePulseReactNativeOtelSpec(reactContext) {
14
21
 
15
22
  override fun getName(): String {
@@ -20,6 +27,11 @@ class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
20
27
  return PulseSDK.INSTANCE.isInitialized()
21
28
  }
22
29
 
30
+ override fun setCurrentScreenName(screenName: String): Boolean {
31
+ ReactNativeScreenNameTracker.setCurrentScreenName(screenName)
32
+ return true
33
+ }
34
+
23
35
  override fun trackEvent(event: String, observedTimeMs: Double, properties: ReadableMap?): Boolean {
24
36
  PulseReactNativeOtelLogger.trackEvent(event, observedTimeMs.toLong(), properties)
25
37
  return true
@@ -30,8 +42,8 @@ class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
30
42
  return true
31
43
  }
32
44
 
33
- override fun startSpan(name: String, attributes: ReadableMap?): String {
34
- return PulseReactNativeOtelTracer.startSpan(name, attributes)
45
+ override fun startSpan(name: String, inheritContext: Boolean, attributes: ReadableMap?): String {
46
+ return PulseReactNativeOtelTracer.startSpan(name, inheritContext, attributes)
35
47
  }
36
48
 
37
49
  override fun endSpan(spanId: String, statusCode: String?): Boolean {
@@ -54,6 +66,11 @@ class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
54
66
  return true
55
67
  }
56
68
 
69
+ override fun discardSpan(spanId: String): Boolean {
70
+ PulseReactNativeOtelTracer.discardSpan(spanId)
71
+ return true
72
+ }
73
+
57
74
  override fun setUserId(id: String?) {
58
75
  PulseSDK.INSTANCE.setUserId(id)
59
76
  }
@@ -79,6 +96,39 @@ class PulseReactNativeOtelModule(reactContext: ReactApplicationContext) :
79
96
  }
80
97
  }
81
98
 
99
+ override fun getAllFeatures(): WritableMap {
100
+ val features = Arguments.createMap()
101
+
102
+ val context = reactApplicationContext
103
+ val sharedPrefs = context.getSharedPreferences(
104
+ "pulse_sdk_config",
105
+ Context.MODE_PRIVATE
106
+ )
107
+
108
+ val configJson = sharedPrefs.getString("sdk_config", null)
109
+ if (configJson != null) {
110
+ val json = Json {
111
+ ignoreUnknownKeys = true
112
+ isLenient = true
113
+ }
114
+ val config = json.decodeFromString<PulseSdkConfig>(configJson)
115
+
116
+ config.features.forEach { featureConfig ->
117
+ if (PulseSdkName.ANDROID_RN in featureConfig.sdks) {
118
+ if (featureConfig.featureName == PulseFeatureName.UNKNOWN) {
119
+ return@forEach
120
+ }
121
+
122
+ val featureNameStr = featureConfig.featureName.name.lowercase()
123
+ val isEnabled = featureConfig.sessionSampleRate > 0F
124
+
125
+ features.putBoolean(featureNameStr, isEnabled)
126
+ }
127
+ }
128
+ }
129
+ return features
130
+ }
131
+
82
132
  companion object {
83
133
  const val NAME = "PulseReactNativeOtel"
84
134
  }
@@ -7,7 +7,7 @@ import com.facebook.react.module.model.ReactModuleInfo
7
7
  import com.facebook.react.module.model.ReactModuleInfoProvider
8
8
  import java.util.HashMap
9
9
 
10
- class PulseReactNativeOtelPackage : BaseReactPackage() {
10
+ internal class PulseReactNativeOtelPackage : BaseReactPackage() {
11
11
  override fun getModule(name: String, reactContext: ReactApplicationContext): NativeModule? {
12
12
  return if (name == PulseReactNativeOtelModule.NAME) {
13
13
  PulseReactNativeOtelModule(reactContext)
@@ -13,7 +13,7 @@ import io.opentelemetry.context.Scope
13
13
  import java.util.UUID
14
14
  import java.util.concurrent.ConcurrentHashMap
15
15
 
16
- object PulseReactNativeOtelTracer {
16
+ internal object PulseReactNativeOtelTracer {
17
17
 
18
18
  private val tracer: Tracer by lazy {
19
19
  PulseSDK.INSTANCE.getOtelOrThrow()
@@ -26,18 +26,20 @@ object PulseReactNativeOtelTracer {
26
26
  private val idToSpan = ConcurrentHashMap<String, Span>()
27
27
  private val idToScope = ConcurrentHashMap<String, Scope>()
28
28
 
29
- fun startSpan(name: String, attributes: ReadableMap?): String {
29
+ fun startSpan(name: String, inheritContext: Boolean, attributes: ReadableMap?): String {
30
30
  val span = tracer.spanBuilder(name)
31
31
  .setSpanKind(SpanKind.INTERNAL)
32
32
  .startSpan()
33
33
 
34
- val scope = span.makeCurrent()
35
-
36
34
  attributes?.applyTo(span)
37
35
 
38
36
  val id = UUID.randomUUID().toString()
39
37
  idToSpan[id] = span
40
- idToScope[id] = scope
38
+
39
+ if (inheritContext) {
40
+ val scope = span.makeCurrent()
41
+ idToScope[id] = scope
42
+ }
41
43
 
42
44
  return id
43
45
  }
@@ -85,6 +87,17 @@ object PulseReactNativeOtelTracer {
85
87
  idToScope.remove(spanId)?.close()
86
88
  }
87
89
 
90
+ fun discardSpan(spanId: String) {
91
+ idToSpan.remove(spanId)?.let { span ->
92
+ span.setAttribute(
93
+ AttributeKey.booleanKey("pulse.internal"),
94
+ true
95
+ )
96
+ span.end()
97
+ }
98
+ idToScope.remove(spanId)?.close()
99
+ }
100
+
88
101
  private fun ReadableMap.applyTo(span: Span) {
89
102
  entryIterator.forEach { (key, value) ->
90
103
  when (value) {
@@ -109,13 +122,16 @@ object PulseReactNativeOtelTracer {
109
122
 
110
123
  when (array.getType(0)) {
111
124
  ReadableType.String -> {
112
- span.setAttribute(AttributeKey.stringArrayKey(key), array.toArrayList() as List<String>)
125
+ @Suppress("UNCHECKED_CAST")
126
+ span.setAttribute(AttributeKey.stringArrayKey(key), array.toArrayList() as List<String>)
113
127
  }
114
128
  ReadableType.Number -> {
115
- span.setAttribute(AttributeKey.doubleArrayKey(key), array.toArrayList() as List<Double>)
129
+ @Suppress("UNCHECKED_CAST")
130
+ span.setAttribute(AttributeKey.doubleArrayKey(key), array.toArrayList() as List<Double>)
116
131
  }
117
132
  ReadableType.Boolean -> {
118
- span.setAttribute(AttributeKey.booleanArrayKey(key), array.toArrayList() as List<Boolean>)
133
+ @Suppress("UNCHECKED_CAST")
134
+ span.setAttribute(AttributeKey.booleanArrayKey(key), array.toArrayList() as List<Boolean>)
119
135
  }
120
136
  else -> {
121
137
  span.setAttribute(AttributeKey.stringKey(key), array.toString())
@@ -0,0 +1,21 @@
1
+ package com.pulsereactnativeotel
2
+
3
+ import io.opentelemetry.android.common.RumConstants
4
+ import io.opentelemetry.context.Context
5
+ import io.opentelemetry.sdk.logs.LogRecordProcessor
6
+ import io.opentelemetry.sdk.logs.ReadWriteLogRecord
7
+
8
+ /**
9
+ * Log record processor that overrides screen.name with React Native screen name.
10
+ */
11
+ internal class ReactNativeScreenAttributesLogRecordProcessor : LogRecordProcessor {
12
+ override fun onEmit(
13
+ context: Context,
14
+ logRecord: ReadWriteLogRecord,
15
+ ) {
16
+ ReactNativeScreenNameTracker.getCurrentScreenName()?.let { screenName ->
17
+ logRecord.setAttribute(RumConstants.SCREEN_NAME_KEY, screenName)
18
+ }
19
+ }
20
+ }
21
+
@@ -0,0 +1,30 @@
1
+ package com.pulsereactnativeotel
2
+
3
+ import io.opentelemetry.android.common.RumConstants
4
+ import io.opentelemetry.context.Context
5
+ import io.opentelemetry.sdk.trace.ReadWriteSpan
6
+ import io.opentelemetry.sdk.trace.ReadableSpan
7
+ import io.opentelemetry.sdk.trace.SpanProcessor
8
+
9
+ /**
10
+ * Span processor that overrides screen.name with React Native screen name.
11
+ */
12
+ internal class ReactNativeScreenAttributesSpanProcessor : SpanProcessor {
13
+ override fun onStart(
14
+ parentContext: Context,
15
+ span: ReadWriteSpan,
16
+ ) {
17
+ ReactNativeScreenNameTracker.getCurrentScreenName()?.let { screenName ->
18
+ span.setAttribute(RumConstants.SCREEN_NAME_KEY, screenName)
19
+ }
20
+ }
21
+
22
+ override fun isStartRequired(): Boolean = true
23
+
24
+ override fun onEnd(span: ReadableSpan) {
25
+ // No-op
26
+ }
27
+
28
+ override fun isEndRequired(): Boolean = false
29
+ }
30
+
@@ -0,0 +1,17 @@
1
+ package com.pulsereactnativeotel
2
+
3
+ import java.util.concurrent.atomic.AtomicReference
4
+
5
+ /**
6
+ * Allows React Native to override Android Activity/Fragment-based screen tracking.
7
+ */
8
+ internal object ReactNativeScreenNameTracker {
9
+ private val currentScreenName = AtomicReference<String?>()
10
+
11
+ fun setCurrentScreenName(screenName: String?) {
12
+ currentScreenName.set(screenName)
13
+ }
14
+
15
+ fun getCurrentScreenName(): String? = currentScreenName.get()
16
+ }
17
+
package/app.plugin.js ADDED
@@ -0,0 +1 @@
1
+ module.exports = require('./plugin/build/index.js');
@@ -35,9 +35,9 @@ RCT_EXPORT_MODULE()
35
35
  return @NO;
36
36
  }
37
37
 
38
- // Start span (returns no-op span ID)
39
38
  - (NSString *)startSpan:(NSString *)name
40
39
  attributes:(NSDictionary *)attributes
40
+ inheritContext:(NSNumber *)inheritContext
41
41
  {
42
42
  return [NSString stringWithFormat:@"noop-ios-%@", [[NSUUID UUID] UUIDString]];
43
43
  }
@@ -71,6 +71,12 @@ RCT_EXPORT_MODULE()
71
71
  return @NO;
72
72
  }
73
73
 
74
+ // Discard span (no-op on iOS)
75
+ - (NSNumber *)discardSpan:(NSString *)spanId
76
+ {
77
+ return @NO;
78
+ }
79
+
74
80
  - (nonnull NSNumber *)reportException:(nonnull NSString *)errorMessage observedTimeMs:(double)observedTimeMs stackTrace:(nonnull NSString *)stackTrace isFatal:(BOOL)isFatal errorType:(nonnull NSString *)errorType attributes:(nonnull NSDictionary *)attributes {
75
81
  return @NO;
76
82
  }
@@ -1 +1 @@
1
- {"version":3,"names":["TurboModuleRegistry","getEnforcing"],"sourceRoot":"../../src","sources":["NativePulseReactNativeOtel.ts"],"mappings":";;AAAA,SAASA,mBAAmB,QAA0B,cAAc;AAwDpE,eAAeA,mBAAmB,CAACC,YAAY,CAAO,sBAAsB,CAAC","ignoreList":[]}
1
+ {"version":3,"names":["TurboModuleRegistry","getEnforcing"],"sourceRoot":"../../src","sources":["NativePulseReactNativeOtel.ts"],"mappings":";;AAAA,SAASA,mBAAmB,QAA0B,cAAc;AAiEpE,eAAeA,mBAAmB,CAACC,YAAY,CAAO,sBAAsB,CAAC","ignoreList":[]}
@@ -2,8 +2,9 @@
2
2
 
3
3
  import { setupErrorHandler } from "./errorHandler.js";
4
4
  import { isSupportedPlatform } from "./initialization.js";
5
- import { createReactNavigationIntegration } from "./reactNavigation.js";
5
+ import { createReactNavigationIntegration } from "./navigation/index.js";
6
6
  import { initializeNetworkInterceptor } from "./network-interceptor/initialization.js";
7
+ import PulseReactNativeOtel from "./NativePulseReactNativeOtel.js";
7
8
  const defaultConfig = {
8
9
  autoDetectExceptions: true,
9
10
  autoDetectNavigation: true,
@@ -12,6 +13,22 @@ const defaultConfig = {
12
13
  let currentConfig = {
13
14
  ...defaultConfig
14
15
  };
16
+
17
+ // Cache for features from remote SDK config
18
+ let cachedFeatures = null;
19
+
20
+ /**
21
+ * Gets all features from the remote SDK config.
22
+ * @returns Record of feature names to their enabled status
23
+ */
24
+ export function getFeaturesFromRemoteConfig() {
25
+ if (cachedFeatures !== null) {
26
+ return cachedFeatures;
27
+ }
28
+ const features = PulseReactNativeOtel.getAllFeatures();
29
+ cachedFeatures = features;
30
+ return cachedFeatures;
31
+ }
15
32
  function configure(config) {
16
33
  currentConfig = {
17
34
  ...currentConfig,
@@ -26,30 +43,33 @@ export function start(options) {
26
43
  if (!isSupportedPlatform()) {
27
44
  return;
28
45
  }
29
- const autoDetectExceptions = options?.autoDetectExceptions ?? true;
30
- const autoDetectNavigation = options?.autoDetectNavigation ?? true;
31
- const autoDetectNetwork = options?.autoDetectNetwork ?? true;
46
+ const features = getFeaturesFromRemoteConfig();
47
+ const autoDetectExceptions = features?.js_crash ?? options?.autoDetectExceptions ?? true;
48
+ const autoDetectNavigation = features?.rn_navigation ?? options?.autoDetectNavigation ?? true;
49
+ const autoDetectNetwork = features?.network_instrumentation ?? options?.autoDetectNetwork ?? true;
32
50
  configure({
33
51
  autoDetectExceptions,
34
52
  autoDetectNavigation,
35
53
  autoDetectNetwork
36
54
  });
37
55
  }
38
- export function createNavigationIntegrationWithConfig() {
56
+ export function createNavigationIntegrationWithConfig(options) {
39
57
  if (!isSupportedPlatform()) {
40
58
  return {
41
- registerNavigationContainer: _ => {}
59
+ registerNavigationContainer: _ => () => {},
60
+ markContentReady: () => {}
42
61
  };
43
62
  }
44
63
  if (!currentConfig.autoDetectNavigation) {
45
64
  console.warn('[Pulse Navigation] auto-detection disabled via Pulse.start; createNavigationIntegration() returning no-op.');
46
65
  const noop = {
47
- registerNavigationContainer: _ => {
66
+ registerNavigationContainer: _ => () => {
48
67
  console.warn('[Pulse Navigation] auto-detection disabled via Pulse.start; registerNavigationContainer() returning no-op.');
49
- }
68
+ },
69
+ markContentReady: () => {}
50
70
  };
51
71
  return noop;
52
72
  }
53
- return createReactNavigationIntegration();
73
+ return createReactNavigationIntegration(options);
54
74
  }
55
75
  //# sourceMappingURL=config.js.map
@@ -1 +1 @@
1
- {"version":3,"names":["setupErrorHandler","isSupportedPlatform","createReactNavigationIntegration","initializeNetworkInterceptor","defaultConfig","autoDetectExceptions","autoDetectNavigation","autoDetectNetwork","currentConfig","configure","config","start","options","createNavigationIntegrationWithConfig","registerNavigationContainer","_","console","warn","noop"],"sourceRoot":"../../src","sources":["config.ts"],"mappings":";;AAAA,SAASA,iBAAiB,QAAQ,mBAAgB;AAClD,SAASC,mBAAmB,QAAQ,qBAAkB;AACtD,SACEC,gCAAgC,QAE3B,sBAAmB;AAC1B,SAASC,4BAA4B,QAAQ,yCAAsC;AAcnF,MAAMC,aAA0B,GAAG;EACjCC,oBAAoB,EAAE,IAAI;EAC1BC,oBAAoB,EAAE,IAAI;EAC1BC,iBAAiB,EAAE;AACrB,CAAC;AAED,IAAIC,aAA0B,GAAG;EAAE,GAAGJ;AAAc,CAAC;AAErD,SAASK,SAASA,CAACC,MAAmB,EAAQ;EAC5CF,aAAa,GAAG;IACd,GAAGA,aAAa;IAChB,GAAGE;EACL,CAAC;EACDV,iBAAiB,CAACQ,aAAa,CAACH,oBAAoB,IAAI,IAAI,CAAC;EAE7D,IAAIG,aAAa,CAACD,iBAAiB,EAAE;IACnCJ,4BAA4B,CAAC,CAAC;EAChC;AACF;AAEA,OAAO,SAASQ,KAAKA,CAACC,OAA2B,EAAQ;EACvD,IAAI,CAACX,mBAAmB,CAAC,CAAC,EAAE;IAC1B;EACF;EACA,MAAMI,oBAAoB,GAAGO,OAAO,EAAEP,oBAAoB,IAAI,IAAI;EAClE,MAAMC,oBAAoB,GAAGM,OAAO,EAAEN,oBAAoB,IAAI,IAAI;EAClE,MAAMC,iBAAiB,GAAGK,OAAO,EAAEL,iBAAiB,IAAI,IAAI;EAC5DE,SAAS,CAAC;IACRJ,oBAAoB;IACpBC,oBAAoB;IACpBC;EACF,CAAC,CAAC;AACJ;AAEA,OAAO,SAASM,qCAAqCA,CAAA,EAA+B;EAClF,IAAI,CAACZ,mBAAmB,CAAC,CAAC,EAAE;IAC1B,OAAO;MACLa,2BAA2B,EAAGC,CAAU,IAAK,CAAC;IAChD,CAAC;EACH;EACA,IAAI,CAACP,aAAa,CAACF,oBAAoB,EAAE;IACvCU,OAAO,CAACC,IAAI,CACV,4GACF,CAAC;IACD,MAAMC,IAAgC,GAAG;MACvCJ,2BAA2B,EAAGC,CAAU,IAAK;QAC3CC,OAAO,CAACC,IAAI,CACV,4GACF,CAAC;MACH;IACF,CAAC;IACD,OAAOC,IAAI;EACb;EACA,OAAOhB,gCAAgC,CAAC,CAAC;AAC3C","ignoreList":[]}
1
+ {"version":3,"names":["setupErrorHandler","isSupportedPlatform","createReactNavigationIntegration","initializeNetworkInterceptor","PulseReactNativeOtel","defaultConfig","autoDetectExceptions","autoDetectNavigation","autoDetectNetwork","currentConfig","cachedFeatures","getFeaturesFromRemoteConfig","features","getAllFeatures","configure","config","start","options","js_crash","rn_navigation","network_instrumentation","createNavigationIntegrationWithConfig","registerNavigationContainer","_","markContentReady","console","warn","noop"],"sourceRoot":"../../src","sources":["config.ts"],"mappings":";;AAAA,SAASA,iBAAiB,QAAQ,mBAAgB;AAClD,SAASC,mBAAmB,QAAQ,qBAAkB;AACtD,SACEC,gCAAgC,QAG3B,uBAAc;AACrB,SAASC,4BAA4B,QAAQ,yCAAsC;AACnF,OAAOC,oBAAoB,MAAM,iCAA8B;AAe/D,MAAMC,aAA0B,GAAG;EACjCC,oBAAoB,EAAE,IAAI;EAC1BC,oBAAoB,EAAE,IAAI;EAC1BC,iBAAiB,EAAE;AACrB,CAAC;AAED,IAAIC,aAA0B,GAAG;EAAE,GAAGJ;AAAc,CAAC;;AAErD;AACA,IAAIK,cAAkC,GAAG,IAAI;;AAE7C;AACA;AACA;AACA;AACA,OAAO,SAASC,2BAA2BA,CAAA,EAAuB;EAChE,IAAID,cAAc,KAAK,IAAI,EAAE;IAC3B,OAAOA,cAAc;EACvB;EAEA,MAAME,QAAQ,GAAGR,oBAAoB,CAACS,cAAc,CAAC,CAAC;EACtDH,cAAc,GAAGE,QAA8B;EAC/C,OAAOF,cAAc;AACvB;AAEA,SAASI,SAASA,CAACC,MAAmB,EAAQ;EAC5CN,aAAa,GAAG;IACd,GAAGA,aAAa;IAChB,GAAGM;EACL,CAAC;EACDf,iBAAiB,CAACS,aAAa,CAACH,oBAAoB,IAAI,IAAI,CAAC;EAE7D,IAAIG,aAAa,CAACD,iBAAiB,EAAE;IACnCL,4BAA4B,CAAC,CAAC;EAChC;AACF;AAEA,OAAO,SAASa,KAAKA,CAACC,OAA2B,EAAQ;EACvD,IAAI,CAAChB,mBAAmB,CAAC,CAAC,EAAE;IAC1B;EACF;EACA,MAAMW,QAAQ,GAAGD,2BAA2B,CAAC,CAAC;EAC9C,MAAML,oBAAoB,GACxBM,QAAQ,EAAEM,QAAQ,IAAID,OAAO,EAAEX,oBAAoB,IAAI,IAAI;EAC7D,MAAMC,oBAAoB,GACxBK,QAAQ,EAAEO,aAAa,IAAIF,OAAO,EAAEV,oBAAoB,IAAI,IAAI;EAClE,MAAMC,iBAAiB,GACrBI,QAAQ,EAAEQ,uBAAuB,IAAIH,OAAO,EAAET,iBAAiB,IAAI,IAAI;EAEzEM,SAAS,CAAC;IACRR,oBAAoB;IACpBC,oBAAoB;IACpBC;EACF,CAAC,CAAC;AACJ;AAEA,OAAO,SAASa,qCAAqCA,CACnDJ,OAAsC,EACV;EAC5B,IAAI,CAAChB,mBAAmB,CAAC,CAAC,EAAE;IAC1B,OAAO;MACLqB,2BAA2B,EAAGC,CAAU,IAAK,MAAM,CAAC,CAAC;MACrDC,gBAAgB,EAAEA,CAAA,KAAM,CAAC;IAC3B,CAAC;EACH;EACA,IAAI,CAACf,aAAa,CAACF,oBAAoB,EAAE;IACvCkB,OAAO,CAACC,IAAI,CACV,4GACF,CAAC;IACD,MAAMC,IAAgC,GAAG;MACvCL,2BAA2B,EAAGC,CAAU,IAAK,MAAM;QACjDE,OAAO,CAACC,IAAI,CACV,4GACF,CAAC;MACH,CAAC;MACDF,gBAAgB,EAAEA,CAAA,KAAM,CAAC;IAC3B,CAAC;IACD,OAAOG,IAAI;EACb;EACA,OAAOzB,gCAAgC,CAACe,OAAO,CAAC;AAClD","ignoreList":[]}
@@ -1 +1 @@
1
- {"version":3,"names":["React","Pulse","jsx","_jsx","UNKNOWN_COMPONENT","COMPONENT_STACK_UNAVAILABLE","INITIAL_STATE","componentStack","error","ErrorBoundary","Component","state","componentDidCatch","errorInfo","onError","props","handled","fallback","errorToReport","Error","String","reportException","setState","render","children","element","createElement","isValidElement","withErrorBoundary","WrappedComponent","errorBoundaryOptions","componentDisplayName","displayName","name","Wrapped","memo"],"sourceRoot":"../../src","sources":["errorBoundary.tsx"],"mappings":";;AAAA,OAAO,KAAKA,KAAK,MAAM,OAAO;AAC9B,SAASC,KAAK,QAAQ,YAAS;AAAC,SAAAC,GAAA,IAAAC,IAAA;AAEhC,OAAO,MAAMC,iBAAiB,GAAG,SAAS;AAC1C,MAAMC,2BAA2B,GAAG,+BAA+B;AAuBnE,MAAMC,aAAiC,GAAG;EACxCC,cAAc,EAAE,IAAI;EACpBC,KAAK,EAAE;AACT,CAAC;AAED,OAAO,MAAMC,aAAa,SAAST,KAAK,CAACU,SAAS,CAAyC;EAClFC,KAAK,GAAuBL,aAAa;EAEzCM,iBAAiBA,CAACJ,KAAc,EAAEK,SAA0B,EAAQ;IACzE,MAAMN,cAAc,GAAGM,SAAS,CAACN,cAAc,IAAIF,2BAA2B;IAC9E,MAAM;MAAES;IAAQ,CAAC,GAAG,IAAI,CAACC,KAAK;;IAE9B;IACA,MAAMC,OAAO,GAAG,CAAC,CAAC,IAAI,CAACD,KAAK,CAACE,QAAQ;IAErC,MAAMC,aAAa,GAAGV,KAAK,YAAYW,KAAK,GAAGX,KAAK,GAAG,IAAIW,KAAK,CAACC,MAAM,CAACZ,KAAK,CAAC,CAAC;IAC/EP,KAAK,CAACoB,eAAe,CAACH,aAAa,EAAE,CAACF,OAAO,CAAC;IAE9C,IAAIF,OAAO,EAAE;MACXA,OAAO,CAACN,KAAK,EAAED,cAAc,CAAC;IAChC;IAEA,IAAI,CAACe,QAAQ,CAAC;MAAEd,KAAK;MAAED;IAAe,CAAC,CAAC;EAC1C;EAEOgB,MAAMA,CAAA,EAAoB;IAC/B,MAAM;MAAEN,QAAQ;MAAEO;IAAS,CAAC,GAAG,IAAI,CAACT,KAAK;IACzC,MAAMJ,KAAK,GAAG,IAAI,CAACA,KAAK;IAExB,IAAIA,KAAK,CAACJ,cAAc,KAAK,IAAI,EAAE;MACjC,OAAO,OAAOiB,QAAQ,KAAK,UAAU,GAAGA,QAAQ,CAAC,CAAC,GAAGA,QAAQ;IAC/D;IAEA,MAAMC,OAAO,GACX,OAAOR,QAAQ,KAAK,UAAU,gBAC1BjB,KAAK,CAAC0B,aAAa,CAACT,QAAQ,EAAE;MAC5BT,KAAK,EAAEG,KAAK,CAACH,KAAK;MAClBD,cAAc,EAAEI,KAAK,CAACJ;IACxB,CAAC,CAAC,GACFU,QAAQ;IAEd,iBAAIjB,KAAK,CAAC2B,cAAc,CAACF,OAAO,CAAC,EAAE;MACjC,OAAOA,OAAO;IAChB;IAEA,OAAO,IAAI;EACb;AACF;AAEA,OAAO,SAASG,iBAAiBA,CAC/BC,gBAAwC,EACxCC,oBAAwC,EAC3B;EACb,MAAMC,oBAAoB,GAAGF,gBAAgB,CAACG,WAAW,IAAIH,gBAAgB,CAACI,IAAI,IAAI7B,iBAAiB;EAEvG,MAAM8B,OAAO,gBAAGlC,KAAK,CAACmC,IAAI,CAAEpB,KAAQ,iBAClCZ,IAAA,CAACM,aAAa;IAAA,GAAKqB,oBAAoB;IAAAN,QAAA,eACrCrB,IAAA,CAAC0B,gBAAgB;MAAA,GAAKd;IAAK,CAAG;EAAC,CAClB,CAChB,CAA2B;EAE5BmB,OAAO,CAACF,WAAW,GAAG,iBAAiBD,oBAAoB,GAAG;EAE9D,OAAOG,OAAO;AAChB","ignoreList":[]}
1
+ {"version":3,"names":["React","Pulse","jsx","_jsx","UNKNOWN_COMPONENT","COMPONENT_STACK_UNAVAILABLE","INITIAL_STATE","componentStack","error","ErrorBoundary","Component","state","componentDidCatch","errorInfo","onError","props","handled","fallback","errorToReport","Error","String","reportException","setState","render","children","element","createElement","isValidElement","withErrorBoundary","WrappedComponent","errorBoundaryOptions","componentDisplayName","displayName","name","Wrapped","memo"],"sourceRoot":"../../src","sources":["errorBoundary.tsx"],"mappings":";;AAAA,OAAO,KAAKA,KAAK,MAAM,OAAO;AAC9B,SAASC,KAAK,QAAQ,YAAS;AAAC,SAAAC,GAAA,IAAAC,IAAA;AAEhC,OAAO,MAAMC,iBAAiB,GAAG,SAAS;AAC1C,MAAMC,2BAA2B,GAAG,+BAA+B;AAuBnE,MAAMC,aAAiC,GAAG;EACxCC,cAAc,EAAE,IAAI;EACpBC,KAAK,EAAE;AACT,CAAC;AAED,OAAO,MAAMC,aAAa,SAAST,KAAK,CAACU,SAAS,CAGhD;EACOC,KAAK,GAAuBL,aAAa;EAEzCM,iBAAiBA,CAACJ,KAAc,EAAEK,SAA0B,EAAQ;IACzE,MAAMN,cAAc,GAClBM,SAAS,CAACN,cAAc,IAAIF,2BAA2B;IACzD,MAAM;MAAES;IAAQ,CAAC,GAAG,IAAI,CAACC,KAAK;;IAE9B;IACA,MAAMC,OAAO,GAAG,CAAC,CAAC,IAAI,CAACD,KAAK,CAACE,QAAQ;IAErC,MAAMC,aAAa,GACjBV,KAAK,YAAYW,KAAK,GAAGX,KAAK,GAAG,IAAIW,KAAK,CAACC,MAAM,CAACZ,KAAK,CAAC,CAAC;IAC3DP,KAAK,CAACoB,eAAe,CAACH,aAAa,EAAE,CAACF,OAAO,CAAC;IAE9C,IAAIF,OAAO,EAAE;MACXA,OAAO,CAACN,KAAK,EAAED,cAAc,CAAC;IAChC;IAEA,IAAI,CAACe,QAAQ,CAAC;MAAEd,KAAK;MAAED;IAAe,CAAC,CAAC;EAC1C;EAEOgB,MAAMA,CAAA,EAAoB;IAC/B,MAAM;MAAEN,QAAQ;MAAEO;IAAS,CAAC,GAAG,IAAI,CAACT,KAAK;IACzC,MAAMJ,KAAK,GAAG,IAAI,CAACA,KAAK;IAExB,IAAIA,KAAK,CAACJ,cAAc,KAAK,IAAI,EAAE;MACjC,OAAO,OAAOiB,QAAQ,KAAK,UAAU,GAAGA,QAAQ,CAAC,CAAC,GAAGA,QAAQ;IAC/D;IAEA,MAAMC,OAAO,GACX,OAAOR,QAAQ,KAAK,UAAU,gBAC1BjB,KAAK,CAAC0B,aAAa,CAACT,QAAQ,EAAE;MAC5BT,KAAK,EAAEG,KAAK,CAACH,KAAK;MAClBD,cAAc,EAAEI,KAAK,CAACJ;IACxB,CAAC,CAAC,GACFU,QAAQ;IAEd,iBAAIjB,KAAK,CAAC2B,cAAc,CAACF,OAAO,CAAC,EAAE;MACjC,OAAOA,OAAO;IAChB;IAEA,OAAO,IAAI;EACb;AACF;AAEA,OAAO,SAASG,iBAAiBA,CAC/BC,gBAAwC,EACxCC,oBAAwC,EAC3B;EACb,MAAMC,oBAAoB,GACxBF,gBAAgB,CAACG,WAAW,IAAIH,gBAAgB,CAACI,IAAI,IAAI7B,iBAAiB;EAE5E,MAAM8B,OAAO,gBAAGlC,KAAK,CAACmC,IAAI,CAAEpB,KAAQ,iBAClCZ,IAAA,CAACM,aAAa;IAAA,GAAKqB,oBAAoB;IAAAN,QAAA,eACrCrB,IAAA,CAAC0B,gBAAgB;MAAA,GAAKd;IAAK,CAAG;EAAC,CAClB,CAChB,CAA2B;EAE5BmB,OAAO,CAACF,WAAW,GAAG,iBAAiBD,oBAAoB,GAAG;EAE9D,OAAOG,OAAO;AAChB","ignoreList":[]}