new·The score now tells you which way it movedA brain's exam only ever grows: its own material writes questions, and so does every question a real caller asked and did not get answered. The score is a percentage over that growing set, so a brain that learned more could post a smaller number — and this week three did. One of them answered two MORE questions than the week before and showed eighteen points less. Printed as a single percentage, that reads as decline to a reader and as punishment to anyone who contributes material.all news →
mozg.beta
Sign in

Expo & React Native · all subjects

eas observe

25 notes, read out of this brain and free to use. Each one was extracted from a source and is re-checked against its exam.

Expo Router integration for EAS Observe prerequisites

The Expo Router integration for EAS Observe requires Expo SDK 56 or later. On earlier SDKs, expo-observe tracks app-wide metrics but per-route navigation events are not emitted. The app must already have EAS Observe installed with expo-observe package. Expo Router must be installed in the app; if not installed, the integration becomes a silent no-op.

Enable Expo Router integration in EAS Observe

Call Observe.configure() with the expo-router integration flag at module scope, before any screen mounts. The integration must be enabled before mount and cannot be toggled at runtime. Calling configure() after the app has mounted, or toggling the flag mid-session, throws an error. Example: Observe.configure({ integrations: { 'expo-router': true } })

Filter sensitive URL parameters in EAS Observe Expo Router integration

Available in SDK 57 and later. Pass sensitive parameter keys to filteredParams in Observe.configure() to remove them from routeParams. When parameters are filtered, the event omits url and includes urlHidden: true instead. routeName is not affected because it is a pattern and never contains parameter values. Example: Observe.configure({ integrations: { 'expo-router': { filteredParams: ['userId', 'token'] } } })

warm_ttr metric: Per-route warm render timing

warm_ttr measures time from navigation dispatch to screen focus for screens that were already rendered before focus, typically because they were preloaded via Link prefetch or user navigated back. Event params: routeName (string, route pattern), url (string, resolved pathname), urlHidden (boolean, present as true when url is omitted due to filtered parameter), routeParams (object, resolved route params).

routeName is a pattern, not a resolved URL

routeName is a route pattern (for example /(tabs)/sessions/[sessionId]), not a resolved URL (for example /sessions/abc). This keeps metrics stable across distinct parameter values so the dashboard buckets them together. Resolved values are still available on the event via url and routeParams.

router.prefetch does not seed cold_ttr or warm_ttr

Calls to router.prefetch() do not count as user navigation and never seed a cold_ttr or warm_ttr measurement. The next user-driven navigation to that route emits warm_ttr because the screen has already rendered.

markInteractive outside screen component error

If markInteractive() logs 'Calling markInteractive on unmounted screen' or 'No metadata available for the current screen', the call ran outside a screen component or after unmount. Move the call into a useEffect inside the screen component.

EAS Insights dashboard tabs

EAS Insights is a dashboard that surfaces trends across your project, grouped into three tabs: App usage (usage of your app across platforms, app store versions, and time, aggregated from EAS Update requests and the expo-insights library), Workflows (run counts, success rates, and trends for EAS Workflows), and Maestro (pass, flake, and failure trends for Maestro end-to-end tests run in EAS Workflows).

EAS Observe performance monitoring metrics

EAS Observe is a performance monitoring service from Expo that tracks how your app performs in production, giving visibility in startup metrics (cold launch time, time to first render, time to interactive), rendering performance, and app user experience across different devices, networks, and conditions. It also records user-defined events that you log from your app to track custom signals alongside performance data.

React Navigation integration available in SDK 56+

The React Navigation integration for EAS Observe is available on SDK 56 and later. On earlier SDKs, expo-observe still tracks app-wide metrics, but per-screen navigation events are not emitted.

React Navigation integration requires @react-navigation/native v7+

The integration depends on @react-navigation/native (v7.0.0 or later) at runtime. If the package is not installed, the integration becomes a silent no-op.

Observe.configure() must be called before app mount

The integration must be enabled before mount and cannot be toggled at runtime. Calling configure() after the app has mounted, or toggling the flag mid-session, throws an error.

Enable React Navigation integration with Observe.configure()

Call Observe.configure() with the 'react-navigation' integration flag at module scope, before any screen mounts. Example: Observe.configure({ integrations: { 'react-navigation': true } });

Use ObserveNavigationContainer with dynamic React Navigation config

For dynamic configuration, replace your top-level NavigationContainer with ObserveNavigationContainer. It wraps the stock container, accepts the same props, and forwards the same ref. It also subscribes to navigation state changes so it can record per-screen render timings.

Use ObserveNavigationProvider with static React Navigation config

With static configuration, create the navigation ref yourself using useNavigationContainerRef(), pass it to the returned Navigation element, and wrap the element in ObserveNavigationProvider with the same ref. The provider listens to navigation events through the ref and records per-screen render timings. ObserveNavigationProvider does not render a container of its own and must be an ancestor of every screen so that useObserve() works inside them.

useObserve() hook provides markInteractive scoped to current screen

Use the useObserve() hook to get a markInteractive function that is automatically scoped to the current screen. The emitted event is tagged with the screen's path. If the integration is disabled or @react-navigation/native is not installed, useObserve() falls back to the global AppMetrics.markInteractive.

Filter sensitive route parameters in React Navigation integration (SDK 57+)

Available in SDK 57 and later. Pass sensitive parameter keys to filteredParams in Observe.configure() to remove them from routeParams. The integration removes filtered keys and includes urlHidden: true on the event. routeName is not affected because it is built from route names and never contains parameter values. Example: Observe.configure({ integrations: { 'react-navigation': { filteredParams: ['userId', 'token'] } } });

cold_ttr metric measures first render time per screen

cold_ttr measures time from when a navigation action is dispatched (for example, navigation.navigate()) to when the destination screen first becomes focused. For the very first focus after app launch, the measurement is taken from when the JS bundle is loaded, and the event includes isAppLaunch: true. Event params: routeName (string, route-name path like /Tabs/Sessions), urlHidden (boolean, present as true when a route parameter was filtered), routeParams (object, focused route params like { sessionId: 'abc' }), isAppLaunch (boolean, true when measured against process start, false for subsequent navigation).

warm_ttr metric measures re-render time for previously rendered screens

warm_ttr measures time from when a navigation action is dispatched to when a screen first becomes focused, but for screens that were already rendered before focus, typically because they were preloaded or the user navigated back to them. Tab-navigator siblings count as warm only once they have been mounted. With React Navigation v7's default lazy: true, unfocused tabs stay unmounted and their first focus is recorded as cold_ttr. Event params: routeName (string, route-name path like /Tabs/Sessions), urlHidden (boolean, present as true when a route parameter was filtered), routeParams (object, focused route params like { sessionId: 'abc' }).

tti metric measures time to interactive per screen

tti (time to interactive) measures time from when a navigation action is dispatched to when markInteractive() is called on the destination screen. Only the first call per navigation is recorded, so it is safe to call markInteractive() multiple times. Event params: routeName (string, route-name path like /Tabs/Sessions), urlHidden (boolean, present as true when a route parameter was filtered), routeParams (object, focused route params), and any custom params passed via markInteractive({ ... }).

routeName built from route names not params for stable metrics

routeName is built from route names (for example /Tabs/Sessions), so route params never appear in the path. This keeps metrics stable across distinct param values so the dashboard buckets them together. Param values are still available on the event via routeParams.

markInteractive() only records when screen is focused

markInteractive() only records once the screen is focused. Calls made on an unfocused screen update internal state but do not emit a tti event until the screen is focused.

useObserve() must be called inside screen component

Call useObserve() inside the screen component, not in a higher-level wrapper. If the screen's identity changes between renders, the hook logs a warning. If markInteractive() logs 'Calling markInteractive on unmounted screen' or 'No metadata available for the current screen', the call ran outside a screen component or after unmount. Move the call into a useEffect inside the screen component.

Static config navigation ref must be same for both provider and Navigation

With static configuration, pass the same ref to both ObserveNavigationProvider and the Navigation element. If the provider receives a ref that is not connected to a navigation container, no per-screen metrics are emitted.

Use Expo Router integration instead for apps using Expo Router

If your app uses Expo Router, use the Expo Router integration instead of the React Navigation integration. The React Navigation integration is for apps that use React Navigation directly.

Give your agent this brain