@goliapkg/sentori-react-native 3.1.0 → 5.0.0
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.
- package/android/build.gradle +21 -0
- package/android/src/main/java/com/sentori/SentoriCrashHandler.kt +29 -0
- package/android/src/test/java/com/sentori/SentoriCrashHandlerTest.kt +7 -2
- package/android/src/test/resources/robolectric.properties +10 -0
- package/lib/config.d.ts +16 -47
- package/lib/config.d.ts.map +1 -1
- package/lib/config.js +3 -0
- package/lib/config.js.map +1 -1
- package/lib/device.d.ts +5 -0
- package/lib/device.d.ts.map +1 -0
- package/lib/device.js +29 -0
- package/lib/device.js.map +1 -0
- package/lib/emit-hooks.d.ts +7 -0
- package/lib/emit-hooks.d.ts.map +1 -0
- package/lib/emit-hooks.js +24 -0
- package/lib/emit-hooks.js.map +1 -0
- package/lib/error-boundary.d.ts.map +1 -1
- package/lib/error-boundary.js +1 -1
- package/lib/error-boundary.js.map +1 -1
- package/lib/feature-flags.d.ts.map +1 -1
- package/lib/handlers/dev-symbolicate.d.ts +1 -1
- package/lib/handlers/dev-symbolicate.d.ts.map +1 -1
- package/lib/handlers/dev-symbolicate.js +2 -0
- package/lib/handlers/dev-symbolicate.js.map +1 -1
- package/lib/handlers/global.js +1 -1
- package/lib/handlers/global.js.map +1 -1
- package/lib/handlers/lifecycle.js +3 -3
- package/lib/handlers/lifecycle.js.map +1 -1
- package/lib/handlers/network.d.ts +2 -2
- package/lib/handlers/network.d.ts.map +1 -1
- package/lib/handlers/network.js +69 -187
- package/lib/handlers/network.js.map +1 -1
- package/lib/handlers/promise.js +1 -1
- package/lib/handlers/promise.js.map +1 -1
- package/lib/handlers/screenshot.d.ts.map +1 -1
- package/lib/handlers/screenshot.js +3 -12
- package/lib/handlers/screenshot.js.map +1 -1
- package/lib/index.d.ts +31 -109
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +51 -103
- package/lib/index.js.map +1 -1
- package/lib/init.d.ts +3 -150
- package/lib/init.d.ts.map +1 -1
- package/lib/init.js +88 -261
- package/lib/init.js.map +1 -1
- package/lib/long-task-monitor.d.ts +1 -7
- package/lib/long-task-monitor.d.ts.map +1 -1
- package/lib/long-task-monitor.js +37 -58
- package/lib/long-task-monitor.js.map +1 -1
- package/lib/mobile-vitals.d.ts +3 -31
- package/lib/mobile-vitals.d.ts.map +1 -1
- package/lib/mobile-vitals.js +22 -61
- package/lib/mobile-vitals.js.map +1 -1
- package/lib/native-pending.d.ts +3 -0
- package/lib/native-pending.d.ts.map +1 -0
- package/lib/native-pending.js +64 -0
- package/lib/native-pending.js.map +1 -0
- package/lib/navigation.d.ts +3 -17
- package/lib/navigation.d.ts.map +1 -1
- package/lib/navigation.js +32 -133
- package/lib/navigation.js.map +1 -1
- package/lib/netinfo.d.ts +1 -1
- package/lib/netinfo.d.ts.map +1 -1
- package/lib/netinfo.js +2 -2
- package/lib/netinfo.js.map +1 -1
- package/lib/push.d.ts.map +1 -1
- package/lib/push.js +2 -4
- package/lib/push.js.map +1 -1
- package/lib/rage-tap.d.ts.map +1 -1
- package/lib/rage-tap.js +28 -23
- package/lib/rage-tap.js.map +1 -1
- package/lib/replay.d.ts.map +1 -1
- package/lib/replay.js +3 -24
- package/lib/replay.js.map +1 -1
- package/lib/scope.d.ts +7 -0
- package/lib/scope.d.ts.map +1 -0
- package/lib/scope.js +41 -0
- package/lib/scope.js.map +1 -0
- package/lib/transport.d.ts +19 -92
- package/lib/transport.d.ts.map +1 -1
- package/lib/transport.js +75 -288
- package/lib/transport.js.map +1 -1
- package/lib/verbs.d.ts +16 -0
- package/lib/verbs.d.ts.map +1 -0
- package/lib/verbs.js +153 -0
- package/lib/verbs.js.map +1 -0
- package/package.json +5 -5
- package/src/__tests__/iron-rule.test.ts +128 -0
- package/src/__tests__/screenshot.test.ts +0 -2
- package/src/__tests__/transport.test.ts +66 -213
- package/src/__tests__/verbs.test.ts +91 -0
- package/src/config.ts +19 -47
- package/src/device.ts +36 -0
- package/src/emit-hooks.ts +30 -0
- package/src/error-boundary.tsx +1 -1
- package/src/handlers/dev-symbolicate.ts +2 -1
- package/src/handlers/global.ts +1 -1
- package/src/handlers/lifecycle.ts +3 -3
- package/src/handlers/network.ts +95 -211
- package/src/handlers/promise.ts +1 -1
- package/src/handlers/screenshot.ts +3 -11
- package/src/index.ts +81 -215
- package/src/init.ts +94 -446
- package/src/long-task-monitor.ts +42 -64
- package/src/mobile-vitals.ts +22 -82
- package/src/native-pending.ts +92 -0
- package/src/navigation.ts +34 -142
- package/src/netinfo.ts +3 -3
- package/src/push.ts +2 -5
- package/src/rage-tap.tsx +29 -26
- package/src/replay.ts +3 -20
- package/src/scope.ts +50 -0
- package/src/transport.ts +84 -371
- package/src/verbs.ts +198 -0
- package/lib/breadcrumbs.d.ts +0 -18
- package/lib/breadcrumbs.d.ts.map +0 -1
- package/lib/breadcrumbs.js +0 -42
- package/lib/breadcrumbs.js.map +0 -1
- package/lib/bundle-info.d.ts +0 -12
- package/lib/bundle-info.d.ts.map +0 -1
- package/lib/bundle-info.js +0 -73
- package/lib/bundle-info.js.map +0 -1
- package/lib/capture.d.ts +0 -140
- package/lib/capture.d.ts.map +0 -1
- package/lib/capture.js +0 -511
- package/lib/capture.js.map +0 -1
- package/lib/compat/sentry.d.ts +0 -126
- package/lib/compat/sentry.d.ts.map +0 -1
- package/lib/compat/sentry.js +0 -332
- package/lib/compat/sentry.js.map +0 -1
- package/lib/control-channel.d.ts +0 -6
- package/lib/control-channel.d.ts.map +0 -1
- package/lib/control-channel.js +0 -96
- package/lib/control-channel.js.map +0 -1
- package/lib/expo-compat.d.ts +0 -270
- package/lib/expo-compat.d.ts.map +0 -1
- package/lib/expo-compat.js +0 -500
- package/lib/expo-compat.js.map +0 -1
- package/lib/feedback-widget.d.ts +0 -35
- package/lib/feedback-widget.d.ts.map +0 -1
- package/lib/feedback-widget.js +0 -193
- package/lib/feedback-widget.js.map +0 -1
- package/lib/feedback.d.ts +0 -2
- package/lib/feedback.d.ts.map +0 -1
- package/lib/feedback.js +0 -17
- package/lib/feedback.js.map +0 -1
- package/lib/heartbeat.d.ts +0 -9
- package/lib/heartbeat.d.ts.map +0 -1
- package/lib/heartbeat.js +0 -138
- package/lib/heartbeat.js.map +0 -1
- package/lib/index.js.bak +0 -64
- package/lib/install-id.d.ts +0 -17
- package/lib/install-id.d.ts.map +0 -1
- package/lib/install-id.js +0 -125
- package/lib/install-id.js.map +0 -1
- package/lib/lifecycle.d.ts +0 -28
- package/lib/lifecycle.d.ts.map +0 -1
- package/lib/lifecycle.js +0 -73
- package/lib/lifecycle.js.map +0 -1
- package/lib/mask.d.ts +0 -16
- package/lib/mask.d.ts.map +0 -1
- package/lib/mask.js +0 -36
- package/lib/mask.js.map +0 -1
- package/lib/measure.d.ts +0 -4
- package/lib/measure.d.ts.map +0 -1
- package/lib/measure.js +0 -25
- package/lib/measure.js.map +0 -1
- package/lib/metrics.d.ts +0 -24
- package/lib/metrics.d.ts.map +0 -1
- package/lib/metrics.js +0 -81
- package/lib/metrics.js.map +0 -1
- package/lib/pre-crash-sentinel.d.ts +0 -12
- package/lib/pre-crash-sentinel.d.ts.map +0 -1
- package/lib/pre-crash-sentinel.js +0 -116
- package/lib/pre-crash-sentinel.js.map +0 -1
- package/lib/report-security.d.ts +0 -40
- package/lib/report-security.d.ts.map +0 -1
- package/lib/report-security.js +0 -159
- package/lib/report-security.js.map +0 -1
- package/lib/runtime-metrics-fps.d.ts +0 -19
- package/lib/runtime-metrics-fps.d.ts.map +0 -1
- package/lib/runtime-metrics-fps.js +0 -128
- package/lib/runtime-metrics-fps.js.map +0 -1
- package/lib/runtime-metrics-heap.d.ts +0 -13
- package/lib/runtime-metrics-heap.d.ts.map +0 -1
- package/lib/runtime-metrics-heap.js +0 -67
- package/lib/runtime-metrics-heap.js.map +0 -1
- package/lib/runtime-metrics-network.d.ts +0 -23
- package/lib/runtime-metrics-network.d.ts.map +0 -1
- package/lib/runtime-metrics-network.js +0 -99
- package/lib/runtime-metrics-network.js.map +0 -1
- package/lib/runtime-metrics.d.ts +0 -43
- package/lib/runtime-metrics.d.ts.map +0 -1
- package/lib/runtime-metrics.js +0 -115
- package/lib/runtime-metrics.js.map +0 -1
- package/lib/sample-profiler.d.ts +0 -21
- package/lib/sample-profiler.d.ts.map +0 -1
- package/lib/sample-profiler.js +0 -152
- package/lib/sample-profiler.js.map +0 -1
- package/lib/sentinel-context.d.ts +0 -4
- package/lib/sentinel-context.d.ts.map +0 -1
- package/lib/sentinel-context.js +0 -52
- package/lib/sentinel-context.js.map +0 -1
- package/lib/session-tracker.d.ts +0 -6
- package/lib/session-tracker.d.ts.map +0 -1
- package/lib/session-tracker.js +0 -50
- package/lib/session-tracker.js.map +0 -1
- package/lib/stack.d.ts +0 -3
- package/lib/stack.d.ts.map +0 -1
- package/lib/stack.js +0 -7
- package/lib/stack.js.map +0 -1
- package/lib/state-snapshots.d.ts +0 -33
- package/lib/state-snapshots.d.ts.map +0 -1
- package/lib/state-snapshots.js +0 -109
- package/lib/state-snapshots.js.map +0 -1
- package/lib/track.d.ts +0 -34
- package/lib/track.d.ts.map +0 -1
- package/lib/track.js +0 -107
- package/lib/track.js.map +0 -1
- package/lib/trail.d.ts +0 -12
- package/lib/trail.d.ts.map +0 -1
- package/lib/trail.js +0 -28
- package/lib/trail.js.map +0 -1
- package/lib/trust-score.d.ts +0 -20
- package/lib/trust-score.d.ts.map +0 -1
- package/lib/trust-score.js +0 -151
- package/lib/trust-score.js.map +0 -1
- package/lib/types.d.ts +0 -2
- package/lib/types.d.ts.map +0 -1
- package/lib/types.js +0 -4
- package/lib/types.js.map +0 -1
- package/lib/uuid.d.ts +0 -2
- package/lib/uuid.d.ts.map +0 -1
- package/lib/uuid.js +0 -3
- package/lib/uuid.js.map +0 -1
- package/src/__tests__/before-send.test.ts +0 -72
- package/src/__tests__/breadcrumbs.test.ts +0 -44
- package/src/__tests__/capture-replay.test.ts +0 -150
- package/src/__tests__/compat-sentry.test.ts +0 -121
- package/src/__tests__/control-channel.test.ts +0 -111
- package/src/__tests__/install-id.test.ts +0 -60
- package/src/__tests__/long-task-monitor.test.ts +0 -59
- package/src/__tests__/measure.test.ts +0 -45
- package/src/__tests__/navigation.test.ts +0 -175
- package/src/__tests__/push.test.ts +0 -238
- package/src/__tests__/report-security.test.ts +0 -106
- package/src/__tests__/runtime-metrics-instruments.test.ts +0 -109
- package/src/__tests__/runtime-metrics-network.test.ts +0 -78
- package/src/__tests__/sample-profiler.test.ts +0 -59
- package/src/__tests__/stack.test.ts +0 -45
- package/src/__tests__/state-snapshots.test.ts +0 -119
- package/src/__tests__/tracing.test.ts +0 -201
- package/src/__tests__/track.test.ts +0 -91
- package/src/__tests__/uuid.test.ts +0 -41
- package/src/breadcrumbs.ts +0 -57
- package/src/bundle-info.ts +0 -95
- package/src/capture.ts +0 -660
- package/src/compat/sentry.ts +0 -490
- package/src/control-channel.ts +0 -98
- package/src/expo-compat.ts +0 -698
- package/src/feedback-widget.tsx +0 -316
- package/src/feedback.ts +0 -21
- package/src/heartbeat.ts +0 -157
- package/src/install-id.ts +0 -146
- package/src/lifecycle.ts +0 -76
- package/src/mask.ts +0 -41
- package/src/measure.ts +0 -28
- package/src/metrics.ts +0 -94
- package/src/pre-crash-sentinel.ts +0 -140
- package/src/report-security.ts +0 -165
- package/src/runtime-metrics-fps.ts +0 -137
- package/src/runtime-metrics-heap.ts +0 -78
- package/src/runtime-metrics-network.ts +0 -103
- package/src/runtime-metrics.ts +0 -122
- package/src/sample-profiler.ts +0 -169
- package/src/sentinel-context.ts +0 -60
- package/src/session-tracker.ts +0 -53
- package/src/stack.ts +0 -10
- package/src/state-snapshots.ts +0 -133
- package/src/track.ts +0 -123
- package/src/trail.ts +0 -32
- package/src/trust-score.ts +0 -176
- package/src/types.ts +0 -21
- package/src/uuid.ts +0 -2
package/src/rage-tap.tsx
CHANGED
|
@@ -1,22 +1,24 @@
|
|
|
1
|
-
//
|
|
1
|
+
// rage_tap — the first detected warn scenario (design.md §3,
|
|
2
|
+
// category A: 「我按了没反应/反复按」).
|
|
2
3
|
//
|
|
3
|
-
// Wrap
|
|
4
|
-
// `<
|
|
5
|
-
//
|
|
6
|
-
//
|
|
7
|
-
//
|
|
8
|
-
//
|
|
9
|
-
//
|
|
4
|
+
// Wrap the app root (next to ErrorBoundary) with
|
|
5
|
+
// `<RageTapCapture>{children}</RageTapCapture>`. Bubble-phase
|
|
6
|
+
// `onTouchEnd` only — pure observation, no gesture interference.
|
|
7
|
+
//
|
|
8
|
+
// Mini-spec: ≥3 taps on the same native target within 800 ms ⇒ one
|
|
9
|
+
// `warn` event, scenario `rage_tap`, surface = current screen +
|
|
10
|
+
// target id, plus a signal-ring entry. Per-target cooldown resets
|
|
11
|
+
// after firing so a frustrated 10-tap burst is one event, not four.
|
|
10
12
|
|
|
11
13
|
import React, { useCallback, useRef } from 'react';
|
|
12
14
|
import { View, type GestureResponderEvent, type ViewProps } from 'react-native';
|
|
13
15
|
|
|
14
|
-
import {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
} from './
|
|
16
|
+
import { pushSignal } from '@goliapkg/sentori-core';
|
|
17
|
+
|
|
18
|
+
import { getConfig } from './config';
|
|
19
|
+
import { currentScreen } from './navigation';
|
|
20
|
+
import { RAGE_THRESHOLD, RAGE_WINDOW_MS, recordTap } from './rage-tap-detector';
|
|
21
|
+
import { warnDetected } from './verbs';
|
|
20
22
|
|
|
21
23
|
export function RageTapCapture({
|
|
22
24
|
children,
|
|
@@ -25,18 +27,19 @@ export function RageTapCapture({
|
|
|
25
27
|
const recent = useRef<Map<number, number[]>>(new Map());
|
|
26
28
|
|
|
27
29
|
const onTouchEnd = useCallback((e: GestureResponderEvent) => {
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
30
|
+
try {
|
|
31
|
+
const target = e.nativeEvent?.target;
|
|
32
|
+
if (typeof target !== 'number') return;
|
|
33
|
+
pushSignal('tap', { target });
|
|
34
|
+
if (!recordTap(recent.current, target, Date.now())) return;
|
|
35
|
+
if (getConfig()?.detect.rageTap === false) return;
|
|
36
|
+
warnDetected(
|
|
37
|
+
'rage_tap',
|
|
38
|
+
{ screen: currentScreen(), element: String(target) },
|
|
39
|
+
{ taps: RAGE_THRESHOLD, windowMs: RAGE_WINDOW_MS },
|
|
40
|
+
);
|
|
41
|
+
} catch {
|
|
42
|
+
// A detector bug must never reach the host's touch pipeline.
|
|
40
43
|
}
|
|
41
44
|
}, []);
|
|
42
45
|
|
package/src/replay.ts
CHANGED
|
@@ -15,9 +15,8 @@
|
|
|
15
15
|
//
|
|
16
16
|
// Wire schema: docs/replay-encoding-v2.md.
|
|
17
17
|
|
|
18
|
-
import { logger
|
|
18
|
+
import { logger } from '@goliapkg/sentori-core';
|
|
19
19
|
|
|
20
|
-
import { getRegisteredMaskQuery } from './mask';
|
|
21
20
|
import { describeWireframeNative } from './native';
|
|
22
21
|
|
|
23
22
|
declare const __DEV__: boolean | undefined;
|
|
@@ -153,18 +152,11 @@ function captureTick(): void {
|
|
|
153
152
|
logger.debug('replay', 'tick: first invocation');
|
|
154
153
|
_firstTickLogged = true;
|
|
155
154
|
}
|
|
156
|
-
let tickSpan: ReturnType<typeof startSpan> | null = null;
|
|
157
|
-
try {
|
|
158
|
-
tickSpan = startSpan('sentori.replay.tick', { name: 'tick' });
|
|
159
|
-
} catch {
|
|
160
|
-
// never fatal
|
|
161
|
-
}
|
|
162
155
|
try {
|
|
163
156
|
const maskIds = readMaskIds();
|
|
164
157
|
const snapshotJson = _nativeMod?.captureWireframe?.(maskIds);
|
|
165
158
|
if (typeof snapshotJson !== 'string' || snapshotJson.length === 0) {
|
|
166
159
|
handleEmptyTick(snapshotJson);
|
|
167
|
-
tickSpan?.finish({ status: 'ok' });
|
|
168
160
|
return;
|
|
169
161
|
}
|
|
170
162
|
|
|
@@ -173,7 +165,6 @@ function captureTick(): void {
|
|
|
173
165
|
snapshot = JSON.parse(snapshotJson) as NativeFrame;
|
|
174
166
|
} catch (e) {
|
|
175
167
|
logger.warn('replay', 'tick: native JSON parse failed', e);
|
|
176
|
-
tickSpan?.finish({ status: 'error' });
|
|
177
168
|
return;
|
|
178
169
|
}
|
|
179
170
|
|
|
@@ -185,10 +176,7 @@ function captureTick(): void {
|
|
|
185
176
|
if (typeof __DEV__ !== 'undefined' && __DEV__) {
|
|
186
177
|
diagnosticForTick(snapshot, snapshotJson.length);
|
|
187
178
|
}
|
|
188
|
-
tickSpan?.finish({ status: 'ok' });
|
|
189
179
|
} catch (e) {
|
|
190
|
-
if (e instanceof Error) tickSpan?.setTag('error.message', e.message);
|
|
191
|
-
tickSpan?.finish({ status: 'error' });
|
|
192
180
|
logger.warn('replay', 'tick threw', e);
|
|
193
181
|
}
|
|
194
182
|
}
|
|
@@ -326,13 +314,8 @@ function diagnosticForTick(snapshot: NativeFrame, snapshotBytes: number): void {
|
|
|
326
314
|
}
|
|
327
315
|
|
|
328
316
|
function readMaskIds(): string[] {
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
try {
|
|
332
|
-
return q();
|
|
333
|
-
} catch {
|
|
334
|
-
return [];
|
|
335
|
-
}
|
|
317
|
+
// Masking returns with a v1 privacy pass; nothing masks today.
|
|
318
|
+
return [];
|
|
336
319
|
}
|
|
337
320
|
|
|
338
321
|
type ReplayNativeModule = {
|
package/src/scope.ts
ADDED
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
// Ambient scope: the current user and the context patch, attached
|
|
2
|
+
// to every outgoing event. Two verbs own this state (user() and
|
|
3
|
+
// context()); everything else reads it.
|
|
4
|
+
|
|
5
|
+
import { hashIdentities, safeFn } from '@goliapkg/sentori-core';
|
|
6
|
+
import type { User } from '@goliapkg/sentori-core';
|
|
7
|
+
|
|
8
|
+
let _user: User | null = null;
|
|
9
|
+
let _userKey: string | undefined;
|
|
10
|
+
let _context: Record<string, unknown> = {};
|
|
11
|
+
let _hashGeneration = 0;
|
|
12
|
+
|
|
13
|
+
export const setUser = safeFn('user', function setUser(u: User | null): void {
|
|
14
|
+
_user = u;
|
|
15
|
+
_userKey = undefined;
|
|
16
|
+
const generation = ++_hashGeneration;
|
|
17
|
+
if (u === null) return;
|
|
18
|
+
// The wire carries only a salted hash — raw identity never leaves
|
|
19
|
+
// the device (breadth × depth needs distinctness, not identity).
|
|
20
|
+
// Hashing is async (WebCrypto); the verb stays synchronous and the
|
|
21
|
+
// key lands a tick later. Events sent in that gap simply carry no
|
|
22
|
+
// userKey, which only under-counts breadth briefly.
|
|
23
|
+
void hashIdentities({ email: u.email, id: u.id })
|
|
24
|
+
.then((hashes) => {
|
|
25
|
+
if (generation === _hashGeneration) {
|
|
26
|
+
_userKey = hashes.id ?? hashes.email;
|
|
27
|
+
}
|
|
28
|
+
})
|
|
29
|
+
.catch(() => {
|
|
30
|
+
// NEVER rule: no key beats a raw identity on the wire.
|
|
31
|
+
});
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
export const patchContext = safeFn('context', function patchContext(
|
|
35
|
+
patch: Record<string, unknown>,
|
|
36
|
+
): void {
|
|
37
|
+
_context = { ..._context, ...patch };
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
export const currentUserKey = (): string | undefined => _userKey;
|
|
41
|
+
|
|
42
|
+
export const currentContext = (): Record<string, unknown> | undefined =>
|
|
43
|
+
Object.keys(_context).length > 0 ? { ..._context } : undefined;
|
|
44
|
+
|
|
45
|
+
export const __resetForTests = (): void => {
|
|
46
|
+
_user = null;
|
|
47
|
+
_userKey = undefined;
|
|
48
|
+
_context = {};
|
|
49
|
+
_hashGeneration++;
|
|
50
|
+
};
|