@rozenite/require-profiler-plugin
v2.5.0
Published
Metro require profiler for Rozenite.
Readme

A Rozenite plugin that instruments require() calls to profile initial app loading performance in React Native applications.
The Rozenite Require Profiler Plugin instruments require() calls during your React Native app's initial loading to track module initialization times. It helps you identify which modules impact app startup performance and optimize your initial bundle loading.

Features
- Initial App Loading Profiling: Automatically instruments
require()calls during app startup to track initialization times - Flame Graph Visualization: Interactive flame graph showing the module dependency tree with timing information
- Top Modules Table: Every module in a chain ranked by self time, so the slowest ones are readable without hunting through the graph
- Package Rollup: The same chain grouped by npm package, at the granularity dependency decisions are actually made
- Require Chains: For any module, the chain of requires that pulled it in, so "why is this even loaded?" has an answer
- Duplicate Detection: Warns when a package was evaluated from more than one install location
- Chain Browser: Every recorded require chain listed with its duration and module count, filterable by a minimum duration
- Module Search: Filter the table and highlight matching frames in the flame graph
- Startup Performance Insights: Identify slow-loading modules that impact Time to Interactive (TTI)
- Bundle Optimization Candidates: Discover modules that are good candidates for code splitting or lazy loading
- Sub-millisecond Timings: Uses
performance.now()where the runtime provides it, so fast modules no longer all report 0ms - Development Only: The Metro instrumentation is disabled in production builds and its polyfill is stripped from release bundles
Installation
Install the Require Profiler plugin as a dependency:
npm install @rozenite/require-profiler-pluginQuick Start
1. Install the Plugin
npm install @rozenite/require-profiler-plugin2. Configure Metro
Add the require profiler instrumentation to your Metro configuration using the enhanceMetroConfig option in withRozenite:
// metro.config.js
const { getDefaultConfig, mergeConfig } = require('@react-native/metro-config');
const { withRozenite } = require('@rozenite/metro');
const { withRozeniteRequireProfiler } = require('@rozenite/require-profiler-plugin/metro');
const defaultConfig = getDefaultConfig(__dirname);
module.exports = withRozenite(
mergeConfig(defaultConfig, {
// Your existing Metro configuration
}),
{
enabled: process.env.WITH_ROZENITE === 'true',
enhanceMetroConfig: (config) => withRozeniteRequireProfiler(config),
}
);Keep withRozenite's enabled option conditional as above — when it is false,
enhanceMetroConfig never runs and nothing is instrumented. The profiler also
defends itself for the cases that sit outside that gate: it skips instrumentation
when process.env.NODE_ENV is production, and the polyfill it injects is wrapped
in __DEV__, which Metro strips from release bundles. Pass enabled to decide for
yourself:
withRozeniteRequireProfiler(config, { enabled: process.env.PROFILE_REQUIRES === 'true' });3. Integrate with Your App
Add the DevTools hook to your React Native app:
// App.tsx
import { useRequireProfilerDevTools } from '@rozenite/require-profiler-plugin';
function App() {
// Enable Require Profiler DevTools
useRequireProfilerDevTools();
return <YourApp />;
}4. Access DevTools
Start your development server and open React Native DevTools. You'll find the "Metro Require Profiler" panel in the DevTools interface.
Usage
Once configured, the plugin automatically instruments all require() calls in your app and provides:
- Chain List: Every recorded require chain, with its total duration and module count. Use the threshold selector to hide chains below a duration you care about.
- Flame Graph: Interactive visualization of your module dependency tree
- Color-coded by self time, from red (heaviest) through to grey (no own time)
- Click a frame to zoom into it; press
Escapeto zoom back out - Type in the filter box to highlight matching modules
- Top Modules: The same chain as a table, sorted by self time, with total time and the number of times each module was evaluated
- Module Details: Select a module to see its self time, total time, direct dependency count, full path, and the require chain that pulled it in
- Packages: Switch "Group by" to Packages to roll the chain up per npm package. Each package shows its own evaluation time and, separately, its cost including everything it pulled in. Packages evaluated from two install locations are flagged here.
Use Cases
Identifying Slow Startup Modules
The flame graph makes it easy to spot modules that take a long time to initialize during app startup. Look for:
- Red modules (>70% of max time) - These are your slowest modules impacting startup
- Wide modules - Modules that take up a lot of horizontal space in the graph
- Deep dependency chains - Modules that load many dependencies during initial load
Finding Bundle Optimization Candidates
Modules that are good candidates for optimization typically:
- Take significant time to initialize (>100ms) during startup
- Are not needed immediately for the initial app experience
- Have many dependencies that could be deferred
Use the profiler to identify these modules and consider optimization strategies:
// Instead of loading heavy modules at startup:
import HeavyModule from './HeavyModule';
// Consider lazy loading or code splitting:
const HeavyModule = lazy(() => import('./HeavyModule'));
// Or move to conditional/dynamic imports:
if (condition) {
const HeavyModule = await import('./HeavyModule');
}Optimizing App Startup Performance
By identifying and optimizing slow-loading modules, you can:
- Reduce initial bundle size and loading time
- Improve Time to Interactive (TTI) metrics
- Prioritize critical modules for immediate loading
- Optimize dependency chains for faster startup
Made with ❤️ at Callstack
rozenite is an open source project and will always remain free to use. If you think it's cool, please star it 🌟.
Callstack is a group of React and React Native geeks, contact us at [email protected] if you need any help with these or just want to say hi!
Like the project? ⚛️ Join the team who does amazing stuff for clients and drives React Native Open Source! 🔥
