๐ป ๅฎ็ฐ JSX ่ฏญๆณ่ฝฌๆ JS ่ฏญๆณ็็ผ่ฏๅจ / JSX to JavaScript Compiler Implementation
A comprehensive JSX tokenization project with both TypeScript and Rust implementations, featuring a live playground for testing and comparison.
- ๐ TypeScript Implementation: Original finite state machine tokenizer
- ๐ฆ Rust Implementation: High-performance, memory-safe alternative
- ๐ Live Playground: Interactive web interface for testing both implementations
- โก Performance Comparison: Benchmarking tools to compare implementations
- ๐ง Multiple Integration Options: WASM, Vite plugin, and native binary support
- ๐งช Comprehensive Testing: Unit tests and integration tests ensuring compatibility
Try it online: https://sunny-117.github.io/jsx-compilation
Or run locally:
cd playground
npm install
npm run devimport { tokenizer } from './lib/jsx-compilation.js';
const jsx = '<h1 id="title">Hello World</h1>';
const tokens = tokenizer(jsx);
console.log(tokens);use jsx_compilation_rs::tokenizer;
let jsx = r#"<h1 id="title">Hello World</h1>"#;
let tokens = tokenizer(jsx).unwrap();
println!("{:?}", tokens);jsx-compilation/
โโโ src/ # TypeScript implementation
โ โโโ tokenizer.ts # Main tokenizer logic
โ โโโ ast.ts # AST node definitions
โ โโโ ...
โโโ jsx-compilation-rs/ # Rust implementation
โ โโโ src/
โ โ โโโ tokenizer.rs # Rust tokenizer
โ โ โโโ wasm.rs # WASM bindings
โ โ โโโ lib.rs # Library interface
โ โโโ Cargo.toml
โโโ playground/ # Interactive web playground
โ โโโ src/
โ โ โโโ App.tsx # React playground app
โ โโโ vite.config.ts
โโโ tests/ # Test suites
โโโ lib/ # Built JavaScript library
โโโ vite-plugin-jsx-compilation-rs.js # Vite plugin
Both implementations recognize these JSX token types:
LeftParentheses:<RightParentheses:>JSXIdentifier: Element names (div, span, h1)AttributeKey: Attribute names (id, class, onClick)AttributeStringValue: String values ("title")AttributeExpressionValue: Expression values ({value})JSXText: Text content between elementsBackSlash:/for closing tags
The tokenizer uses a finite state machine with these states:
- Start: Expects
< - FoundLeftParentheses: After
<, expects identifier or/ - JSXIdentifier: Collecting element name
- Attribute: Looking for attribute key
- AttributeKey: Collecting attribute name
- AttributeValue: Expecting attribute value
- AttributeStringValue: Inside string value
- AttributeExpressionValue: Inside expression value
- TryLeaveAttribute: After attribute value
- FoundRightParentheses: After
>, expecting text or new element - JSXText: Collecting text content
// vite.config.js
import { jsxCompilationRs } from './vite-plugin-jsx-compilation-rs.js';
export default {
plugins: [
jsxCompilationRs({
rustProjectPath: './jsx-compilation-rs',
useWasm: false, // or true for WASM
})
]
};cd jsx-compilation-rs
./build-wasm.shimport init, { tokenizer } from './jsx-compilation-rs/pkg/jsx_compilation_rs.js';
await init();
const tokens = tokenizer('<div>Hello</div>');cd jsx-compilation-rs
cargo build --release --bin compare
./target/release/compare '<div>Hello</div>'Performance characteristics vary by integration method:
| Method | Pros | Cons | Use Case |
|---|---|---|---|
| TypeScript | Fast in-process execution | Global state issues | Development, simple use |
| Rust Binary | Memory safe, no global state | Process overhead (~3ms) | CLI tools, isolation |
| WASM | Near-native speed, no overhead | Build complexity | Production web apps |
Run benchmarks:
node benchmark.js# TypeScript tests
npm test
# Rust tests
cd jsx-compilation-rs
cargo test
# Integration tests
node compare-implementations.js- โ Basic JSX elements
- โ Nested elements
- โ String attributes
- โ Expression attributes
- โ Multiple attributes
- โ Error cases
- โ Edge cases
- โ State isolation
- Node.js 16+
- Rust 1.70+
- wasm-pack (for WASM builds)
# Install dependencies
npm install
cd playground && npm install
# Build TypeScript
npm run build
# Build Rust
cd jsx-compilation-rs
cargo build --release
# Build WASM
./build-wasm.sh- Make changes to TypeScript or Rust implementation
- Run tests to ensure compatibility
- Test in playground
- Run benchmarks if performance-critical
- Update documentation
- Fork the repository
- Create a feature branch
- Implement changes with tests
- Ensure both implementations remain compatible
- Submit a pull request
MIT License - see LICENSE file for details.
- Original TypeScript implementation for reference
- Rust community for excellent tooling
- React team for JSX specification