npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

react-component-scanner

v1.0.3

Published

A powerful tool to scan React/React Native codebases and generate component dependency graphs with collision resolution and import analysis

Readme

React Component Scanner

A powerful tool to scan React, React Native, Next.js, and Vite codebases and generate comprehensive component dependency graphs with advanced collision resolution and import analysis.

Disclaimer

This project is completely vibe-coded with no coding standard whatsoever. If you want to contribute, you should use Curser.

Why this package

⚠️ This package is not intended to be used on its own.
It was designed to work alongside React Graph, a web-based UI tool that visualizes your component tree and unlocks powerful features using the output generated by this package as input.

🚀 Features

  • Auto Project Detection: Automatically detects project root for React, React Native, Next.js, Vite, and other frameworks
  • Component Discovery: Automatically finds all React components (function, class, arrow, forwardRef, memo)
  • Dependency Graph: Maps parent-child relationships between components
  • Collision Resolution: Handles multiple components with the same name using hash-based unique IDs
  • Import Analysis: Resolves imports with re-export following and path alias support
  • Same-File Priority: Prioritizes components defined in the same file over external imports
  • 🤖 Automatic Screen Detection: Automatically detects screens from navigation patterns (NEW!)
    • React Navigation: Stack.Screen, Tab.Screen, Drawer.Screen patterns
    • React Router: Route element/component patterns
    • Next.js: File-based routing (pages/ and app/ directories)
  • Manual Screen Detection: Identifies screen components based on ScreenContainer usage or manual marking
  • Navigation Flow: Extracts navigation sequences from component properties
  • Entry Route Detection: Identifies application entry points
  • Babel Integration: Dynamically reads path aliases from babel.config.js

📦 Installation

Global Installation

npm install -g react-component-scanner

Use with npx (Recommended)

npx react-component-scanner

🎯 Quick Start

Basic Usage

Define entry point.

By default, DepGraph opens with entry routes. For example, if your app has 5 tabs, mark them all as entry points:

    ComponentName.isEntryRoute = true;
    export default ComponentName;

Define screens

🤖 Automatic Detection (Recommended) The scanner now automatically detects screens from navigation patterns! No manual marking needed for:

  • React Navigation: Components used in Stack.Screen, Tab.Screen, Drawer.Screen
  • React Router: Components used in <Route element={<Component />} /> or <Route component={Component} />
  • Next.js: Components in pages/ directory or app/*/page.tsx files

📝 Manual Detection (Legacy) To manually mark a component as a screen:

    ComponentName.isScreen = true;
    ComponentName.isEntryRoute = true;
    export default ComponentName;

Define custom properties

Custom properties help group similar components. For example, in a car-selling app, multiple card/UI can show car info.

    ListingCard.isCarCard = true;
    export default ListingCard;

Generate dependency graph

  npx react-component-scanner

CLI Options

npx react-component-scanner [directory] [options]

Options:
  -o, --output <file>              Output file for component analysis (default: "component-analysis.json")
  -d, --dependency-graph <file>    Output file for dependency graph (default: "dependency-graph.json")  
  -e, --extensions <extensions>    File extensions to include (default: ".js,.jsx,.ts,.tsx")
  -b, --babel-config <path>        Path to babel.config.js file (default: "./babel.config.js")
  -q, --quiet                      Suppress verbose output
  --no-auto-detect-screens         Disable automatic screen detection from navigation patterns
  --no-save                        Don't save results to files (just output stats)
  -h, --help                       Display help for command

📊 Output Files

Dependency Graph (dependency-graph.json)

Contains the complete component relationship graph:

{
  "totalComponents": 636,
  "scanDate": "2024-01-15T10:30:00.000Z",
  "collisions": 29,
  "dependencyGraph": {
    "a1b2c3d4.Button": {
      "name": "Button",
      "uniqueId": "a1b2c3d4.Button",
      "filePath": "src/components/Button/Button.tsx",
      "absolutePath": "/project/src/components/Button/Button.tsx",
      "type": "function",
      "children": ["Text", "e5f6g7h8.TouchableOpacity"],
      "childrenWithPaths": [
        {
          "name": "Text",
          "path": null
        },
        {
          "name": "e5f6g7h8.TouchableOpacity",
          "path": "/project/src/components/TouchableOpacity/TouchableOpacity.tsx"
        }
      ],
      "properties": {
        "isScreen": false,
        "Remote": true
      }
    }
  }
}

🎨 Component Detection

The scanner detects various types of React components:

Function Components

function MyComponent() {
  return <div>Hello</div>;
}

Arrow Function Components

const MyComponent = () => {
  return <div>Hello</div>;
};

Class Components

class MyComponent extends React.Component {
  render() {
    return <div>Hello</div>;
  }
}

forwardRef Components

const MyComponent = React.forwardRef((props, ref) => {
  return <div ref={ref}>Hello</div>;
});

memo Components

const MyComponent = React.memo(() => {
  return <div>Hello</div>;
});

🤖 Automatic Screen Detection

The scanner automatically detects screens from common navigation patterns without requiring manual isScreen = true annotations.

React Navigation Patterns

// Stack Navigator
const Stack = createStackNavigator();
<Stack.Navigator>
  <Stack.Screen name="Home" component={HomeScreen} />      // ✅ HomeScreen auto-detected
  <Stack.Screen name="Profile" component={ProfileScreen} /> // ✅ ProfileScreen auto-detected
</Stack.Navigator>

// Tab Navigator  
const Tab = createBottomTabNavigator();
<Tab.Navigator>
  <Tab.Screen name="Main" component={MainScreen} />         // ✅ MainScreen auto-detected
  <Tab.Screen name="Settings" component={SettingsScreen} /> // ✅ SettingsScreen auto-detected
</Tab.Navigator>

// Drawer Navigator
const Drawer = createDrawerNavigator();
<Drawer.Navigator>
  <Drawer.Screen name="Home" component={HomeScreen} />      // ✅ HomeScreen auto-detected
</Drawer.Navigator>

React Router Patterns

// React Router v6
<Routes>
  <Route path="/" element={<HomePage />} />          // ✅ HomePage auto-detected
  <Route path="/about" element={<AboutPage />} />    // ✅ AboutPage auto-detected
  <Route path="/contact" component={ContactPage} />  // ✅ ContactPage auto-detected (v5 style)
</Routes>

Next.js File-Based Routing

pages/
  index.tsx        // ✅ Default export auto-detected as screen
  about.tsx        // ✅ Default export auto-detected as screen  
  products/
    index.tsx      // ✅ Default export auto-detected as screen
    [id].tsx       // ✅ Default export auto-detected as screen

app/                // Next.js 13+ App Router
  page.tsx         // ✅ Default export auto-detected as screen
  about/
    page.tsx       // ✅ Default export auto-detected as screen
  products/
    [id]/
      page.tsx     // ✅ Default export auto-detected as screen

Configuration

// Disable automatic detection if needed
const results = scanProject({
  autoDetectScreens: false  // Default: true
});
# CLI: Disable automatic detection
npx react-component-scanner --no-auto-detect-screens

🔍 Advanced Features

Path Alias Resolution

Automatically reads path aliases from your babel.config.js:

// babel.config.js
module.exports = {
  plugins: [
    ['module-resolver', {
      alias: {
        '@components': './src/components',
        '@screens': './src/screens',
        '@utils': './src/utils'
      }
    }]
  ]
};

Component Properties Detection

Detects custom properties assigned to components:

const MyScreen = () => <ScreenContainer>...</ScreenContainer>;

// These properties are automatically detected
MyScreen.isScreen = true;
MyScreen.Remote = true;
MyScreen.navigate = [
  { screen: 'NextScreen', condition: 'success' },
  { screen: 'ErrorScreen', condition: 'failure' }
];

Collision Resolution

Suppose you have multiple components with the same name, the parent will be resolved to have a child with the following preference

  1. Same-file components (highest priority)
  2. Import-resolved components (with re-export following)
  3. First available instance (fallback)

Screen Detection

Automatically identifies screen components:

  • Components with isScreen = true property
  • Components that use ScreenContainer as a child

Navigation Flow Analysis

Extracts navigation sequences from component properties:

PaymentScreen.navigate = [
  { screen: 'SuccessScreen', condition: 'payment_success' },
  { screen: 'FailureScreen', condition: 'payment_failed' }
];

🛠️ Requirements

  • Node.js >= 16.0.0
  • React/React Native project with JSX/TSX files
  • Optional: babel.config.js with module-resolver plugin for path aliases

Troubleshoot

Wrong component is getting linked as children.

  • Please check Collision Resolution section
  • To debug, try to remove, React.memo, React.forwardRef, any hoc before remove
  • Try to have same component import and export name. If component is exported with identifier ShortlistIcon, try to import and use as ShortlistIcon only.
  • If issue is still there then try to create a extract children into a separate file
  • If you still have issue, please fell free to raise issue on github

Made with ❤️ for the React community