Skip to content

PDhvanik/Transpiler-React-Class-to-Function-Component

Repository files navigation

React Class-to-Function Transpiler

A comprehensive Babel-based transpiler that converts React class components into functional components using React Hooks, with advanced compilation visualization and symbol table analysis.

Features

Core Transformation

  • AST Parsing: Uses @babel/parser to create Abstract Syntax Trees
  • Class Component Conversion: Transforms extends React.Component to functional components
  • Hook Migration: Converts lifecycle methods to React Hooks
    • constructor with this.stateuseState hooks
    • componentDidMountuseEffect(() => {}, [])
    • componentDidUpdateuseEffect(() => {}, [dependencies])
    • componentWillUnmountuseEffect cleanup functions
  • State Management: Intelligent this.setState to hook setter conversion
  • Method Conversion: Class methods become internal component functions
  • Props Handling: this.props references converted to function parameters

Advanced Analysis

  • Symbol Table Generation: Comprehensive symbol analysis with:
    • Memory address simulation
    • Scope tracking (global, class, function)
    • Type classification (variable, function, class, method, property, import, export)
    • Value extraction and additional metadata
  • Three-Address Code: Intermediate representation generation
  • Compilation Steps: Complete compilation pipeline visualization

Interactive Visualization

  • Modern Web Dashboard: Clean, icon-free interface
  • AST Tree Viewer: Interactive, collapsible tree structure
  • Symbol Table Browser: Detailed symbol information with filtering
  • Before/After Comparison: Side-by-side code comparison
  • Compilation Steps: Step-by-step transformation process

Installation

This project is configured as an ES Module project ("type": "module").

  1. Clone the repository:
git clone <repository-url>
cd react-class-to-function-transpiler
  1. Install dependencies:
npm install

Usage

Command Line Interface

The transpiler provides a comprehensive CLI with multiple options:

# Basic transformation
node src/cli.js --in <input.js> --out <output.js>

# Print to stdout
node src/cli.js --in <input.js> --print

# AST analysis
node src/cli.js --ast <input.js> --stats

# Help
node src/cli.js --help

CLI Options

  • --in <file>: Input JavaScript/JSX file path
  • --out <file>: Output file path (default: output.js next to input)
  • --print: Print transformed code to stdout
  • --ast <file>: Parse and print AST JSON for given input
  • --stats: With --ast, print AST statistics (node counts by type)
  • -h, --help: Show help information

Interactive Visualization

  1. Generate visualization:
node src/cli.js --in your-component.js --out output.js
  1. Start the visualization server:
node server.js
  1. Open in browser: Navigate to http://localhost:3000

Quick Start Example

# Transform the included complex example
node src/cli.js --in src/complex-input.js --out transformed-output.js

# Start visualization server
node server.js

# Open http://localhost:3000 in your browser

Example Transformation

Input (Class Component)

import React, { Component } from 'react';

class UserDashboard extends Component {
  constructor(props) {
    super(props);
    this.state = {
      userData: null,
      postsData: [],
      searchTerm: '',
      notification: null
    };
  }

  componentDidMount() {
    this.fetchUserData();
    this.setupEventListeners();
  }

  componentDidUpdate(prevProps, prevState) {
    if (prevState.searchTerm !== this.state.searchTerm) {
      this.getFilteredPosts();
    }
  }

  componentWillUnmount() {
    this.removeEventListeners();
  }

  fetchUserData = async () => {
    try {
      const response = await fetch('/api/user');
      const userData = await response.json();
      this.setState({ userData });
    } catch (error) {
      this.addNotification('Failed to fetch user data', 'error');
    }
  };

  handleSearch = (event) => {
    this.setState({ searchTerm: event.target.value });
  };

  render() {
    const { userData, postsData, searchTerm } = this.state;
    
    return (
      <div className="dashboard">
        <h1>Welcome, {userData?.name}</h1>
        <input 
          type="text" 
          value={searchTerm}
          onChange={this.handleSearch}
          placeholder="Search posts..."
        />
        {/* More JSX */}
      </div>
    );
  }
}

export default UserDashboard;

Output (Functional Component)

import React, { useState, useEffect } from 'react';

const UserDashboard = (props) => {
  const [userData, setUserData] = useState(null);
  const [postsData, setPostsData] = useState([]);
  const [searchTerm, setSearchTerm] = useState('');
  const [notification, setNotification] = useState(null);

  const fetchUserData = async () => {
    try {
      const response = await fetch('/api/user');
      const userData = await response.json();
      setUserData(userData);
    } catch (error) {
      addNotification('Failed to fetch user data', 'error');
    }
  };

  const handleSearch = (event) => {
    setSearchTerm(event.target.value);
  };

  useEffect(() => {
    fetchUserData();
    setupEventListeners();
    
    return () => {
      removeEventListeners();
    };
  }, []);

  useEffect(() => {
    getFilteredPosts();
  }, [searchTerm]);

  return (
    <div className="dashboard">
      <h1>Welcome, {userData?.name}</h1>
      <input 
        type="text" 
        value={searchTerm}
        onChange={handleSearch}
        placeholder="Search posts..."
      />
      {/* More JSX */}
    </div>
  );
};

export default UserDashboard;

Project Structure

react-class-to-function-transpiler/
├── src/
│   ├── debug/
│   │   ├── compilerUtils.js      # Enhanced compilation with symbol table
│   │   └── compilationSteps.js   # Step-by-step compilation logging
│   ├── transformers/
│   │   ├── reactClassToFunction.js  # Core transformation logic
│   │   └── dependencyDetection.js  # Hook dependency analysis
│   ├── utils/
│   │   └── helpers.js            # Utility functions
│   ├── cli.js                    # Command-line interface
│   ├── index.js                  # Main entry point
│   ├── parser.js                 # AST parsing utilities
│   ├── transpiler.js             # Core transpiler logic
│   ├── traverse.js               # AST traversal utilities
│   ├── visualizer.js             # Visualization generator
│   └── complex-input.js          # Example complex component
├── compilation-steps/            # Generated compilation artifacts
├── server.js                     # Visualization web server
├── package.json
└── README.md

Symbol Table Features

The transpiler generates comprehensive symbol tables with:

  • ID: Unique identifier for each symbol
  • Name: Symbol identifier name
  • Type: Classification (variable, function, class, method, property, parameter, import, export)
  • Memory Address: Simulated memory location
  • Scope: Context (global, program, class:ClassName, function:functionName)
  • Value: Extracted or inferred value
  • Location: Line and column numbers
  • Additional Info: Context-specific metadata

Compilation Pipeline

  1. Lexical Analysis: Source code tokenization
  2. Syntax Analysis: AST generation using Babel parser
  3. Symbol Table Construction: Comprehensive symbol extraction
  4. Semantic Analysis: Type checking and scope analysis
  5. AST Transformation: React class to function conversion
  6. Code Generation: Final functional component output
  7. Visualization: Interactive compilation dashboard

Supported Transformations

Lifecycle Methods

  • constructoruseState initialization
  • componentDidMountuseEffect(() => {}, [])
  • componentDidUpdateuseEffect(() => {}, [deps])
  • componentWillUnmountuseEffect cleanup
  • getDerivedStateFromPropsuseMemo or conditional logic

State Management

  • this.state.propertyproperty (from useState)
  • this.setState({key: value})setKey(value)
  • Complex state updates with proper hook patterns

Method Conversion

  • Class methods → Internal component functions
  • Arrow function properties → Function declarations
  • Event handlers with proper binding

Props and Context

  • this.propsprops parameter
  • Context consumption patterns
  • Prop destructuring optimization

Limitations

  • Complex lifecycle method combinations may need manual review
  • Advanced patterns like HOCs require additional consideration
  • Static class members are not automatically converted
  • Some edge cases in state updates may need refinement

Contributing

  1. Fork the repository
  2. Create a feature branch
  3. Add tests for new functionality
  4. Ensure all tests pass
  5. Submit a pull request

License

MIT License - see LICENSE file for details

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published