VuReact is a compiler toolchain for migrating from Vue to React — and for writing React with Vue 3 syntax.
In this article, we will look at how Vue SFC <style module> blocks are compiled into React code.
Before We Start
To keep the examples easy to read, this article follows two simple conventions:
- All Vue and React snippets focus on core logic only, with full component wrappers and unrelated configuration omitted.
- The discussion assumes you are already familiar with CSS Modules in Vue 3.
Compilation Mapping
Module style transformation
Vue CSS Modules are transformed into a React-compatible module import format while preserving class-name mapping.
- Vue
<!-- Component.vue -->
<template>
<div :class="$style.container">Hello</div>
</template>
<style module>
.container {
padding: 20px;
background: #f5f5f5;
}
</style>
- Compiled React
// Component.jsx
import $style from './component-abc1234.module.css';
function Component() {
return <div className={$style.container}>Hello</div>;
}
/* component-abc1234.module.css */
.container {
padding: 20px;
background: #f5f5f5;
}
As the example shows, Vue <style module> blocks are compiled into CSS Modules files, then used in React through module imports. That preserves the familiar $style.container access pattern and keeps module scoping intact.
Custom module names
CSS Modules also support named module imports.
- Default module name:
$style->$style - Custom module name:
<style module="custom">->custom
- Vue
<!-- Component.vue -->
<template>
<div :class="custom.container">Custom Module</div>
</template>
<style module="custom">
.container {
margin: 10px;
border: 1px solid #ccc;
}
</style>
- Compiled React
// Component.jsx
import custom from './component-xyz123.module.css';
function Component() {
return <div className={custom.container}>Custom Module</div>;
}
The generated code keeps the module import style consistent with Vue's usage while adapting it to React's module import conventions.
CSS Modules with scoped styles
CSS Modules can also be combined with scoped styles for stronger isolation.
- Vue
<!-- Component.vue -->
<template>
<div :class="$style.wrapper">
<span :class="$style.text">Text Content</span>
</div>
</template>
<style module scoped>
.wrapper {
padding: 20px;
background: #f8f8f8;
}
.text {
color: #333;
font-size: 16px;
}
</style>
- Compiled React
// Component.jsx
import $style from './component-abc123.module.css';
function Component() {
return (
<div className={$style.wrapper} data-css-abc123>
<span className={$style.text} data-css-abc123>
Text Content
</span>
</div>
);
}
/* component-abc123.module.css */
.wrapper[data-css-abc123] {
padding: 20px;
background: #f8f8f8;
}
.text[data-css-abc123] {
color: #333;
font-size: 16px;
}
The combination of scoped plus CSS Modules gives you both module-level encapsulation and per-component style isolation.
Compilation summary
VuReact's CSS Modules compilation strategy shows a complete module-style migration path:
- CSS Modules are extracted into standalone
.module.cssfiles. - Class mappings are preserved, including
$style.classNamesyntax. - React-compatible module imports are generated automatically.
That lets the compiled React output keep Vue's CSS Modules experience while fitting naturally into React's module-based styling model.
Top comments (0)