react-client 1.0.16 ā 1.0.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/commands/dev.js +55 -31
- package/package.json +1 -1
package/dist/cli/commands/dev.js
CHANGED
|
@@ -24,7 +24,7 @@ async function dev() {
|
|
|
24
24
|
const defaultPort = userConfig.server?.port || 5173;
|
|
25
25
|
const cacheDir = path_1.default.join(appRoot, '.react-client', 'deps');
|
|
26
26
|
await fs_extra_1.default.ensureDir(cacheDir);
|
|
27
|
-
//
|
|
27
|
+
// š Dynamically detect entry (main.tsx or main.jsx)
|
|
28
28
|
const possibleEntries = ['src/main.tsx', 'src/main.jsx'];
|
|
29
29
|
const entry = possibleEntries.map((p) => path_1.default.join(appRoot, p)).find((p) => fs_extra_1.default.existsSync(p));
|
|
30
30
|
if (!entry) {
|
|
@@ -32,7 +32,7 @@ async function dev() {
|
|
|
32
32
|
process.exit(1);
|
|
33
33
|
}
|
|
34
34
|
const indexHtml = path_1.default.join(appRoot, 'index.html');
|
|
35
|
-
//
|
|
35
|
+
// š§ Port selection
|
|
36
36
|
const availablePort = await (0, detect_port_1.default)(defaultPort);
|
|
37
37
|
const port = availablePort;
|
|
38
38
|
if (availablePort !== defaultPort) {
|
|
@@ -47,7 +47,7 @@ async function dev() {
|
|
|
47
47
|
process.exit(0);
|
|
48
48
|
}
|
|
49
49
|
}
|
|
50
|
-
// ā”
|
|
50
|
+
// ā” Ensure react-refresh runtime installed
|
|
51
51
|
function safeResolveReactRefresh() {
|
|
52
52
|
try {
|
|
53
53
|
return require.resolve('react-refresh/runtime');
|
|
@@ -61,9 +61,8 @@ async function dev() {
|
|
|
61
61
|
return require.resolve('react-refresh/runtime');
|
|
62
62
|
}
|
|
63
63
|
}
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
// --- Plugins (core + user)
|
|
64
|
+
void safeResolveReactRefresh();
|
|
65
|
+
// š§© Core + user plugins
|
|
67
66
|
const corePlugins = [
|
|
68
67
|
{
|
|
69
68
|
name: 'css-hmr',
|
|
@@ -71,12 +70,12 @@ async function dev() {
|
|
|
71
70
|
if (id.endsWith('.css')) {
|
|
72
71
|
const escaped = JSON.stringify(code);
|
|
73
72
|
return `
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
73
|
+
const css = ${escaped};
|
|
74
|
+
const style = document.createElement('style');
|
|
75
|
+
style.textContent = css;
|
|
76
|
+
document.head.appendChild(style);
|
|
77
|
+
import.meta.hot && import.meta.hot.accept();
|
|
78
|
+
`;
|
|
80
79
|
}
|
|
81
80
|
return code;
|
|
82
81
|
},
|
|
@@ -84,10 +83,10 @@ async function dev() {
|
|
|
84
83
|
];
|
|
85
84
|
const userPlugins = Array.isArray(userConfig.plugins) ? userConfig.plugins : [];
|
|
86
85
|
const plugins = [...corePlugins, ...userPlugins];
|
|
87
|
-
//
|
|
86
|
+
// š Connect app + caches
|
|
88
87
|
const app = (0, connect_1.default)();
|
|
89
88
|
const transformCache = new Map();
|
|
90
|
-
//
|
|
89
|
+
// š¦ Prebundle persistent deps
|
|
91
90
|
async function prebundleDeps() {
|
|
92
91
|
const pkgFile = path_1.default.join(appRoot, 'package.json');
|
|
93
92
|
if (!fs_extra_1.default.existsSync(pkgFile))
|
|
@@ -117,13 +116,13 @@ async function dev() {
|
|
|
117
116
|
console.log(chalk_1.default.green(`ā
Cached ${dep}`));
|
|
118
117
|
}
|
|
119
118
|
catch (err) {
|
|
120
|
-
const
|
|
121
|
-
console.warn(chalk_1.default.yellow(`ā ļø Skipped ${dep}: ${
|
|
119
|
+
const e = err;
|
|
120
|
+
console.warn(chalk_1.default.yellow(`ā ļø Skipped ${dep}: ${e.message}`));
|
|
122
121
|
}
|
|
123
122
|
}
|
|
124
123
|
}
|
|
125
124
|
await prebundleDeps();
|
|
126
|
-
// --- Serve prebundled modules
|
|
125
|
+
// --- Serve prebundled modules (fixed resolver)
|
|
127
126
|
app.use('/@modules/', async (req, res, next) => {
|
|
128
127
|
const id = req.url?.replace(/^\/@modules\//, '');
|
|
129
128
|
if (!id)
|
|
@@ -134,7 +133,23 @@ async function dev() {
|
|
|
134
133
|
res.setHeader('Content-Type', 'application/javascript');
|
|
135
134
|
return res.end(await fs_extra_1.default.readFile(cacheFile));
|
|
136
135
|
}
|
|
137
|
-
|
|
136
|
+
let entryPath = null;
|
|
137
|
+
try {
|
|
138
|
+
entryPath = require.resolve(id, { paths: [path_1.default.join(appRoot, 'node_modules')] });
|
|
139
|
+
}
|
|
140
|
+
catch {
|
|
141
|
+
try {
|
|
142
|
+
entryPath = require.resolve(id, { paths: [root] });
|
|
143
|
+
}
|
|
144
|
+
catch {
|
|
145
|
+
if (id === 'react')
|
|
146
|
+
entryPath = require.resolve('react');
|
|
147
|
+
else if (id === 'react-dom' || id === 'react-dom/client')
|
|
148
|
+
entryPath = require.resolve('react-dom');
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
if (!entryPath)
|
|
152
|
+
throw new Error(`Could not resolve ${id}`);
|
|
138
153
|
const result = await esbuild_1.default.build({
|
|
139
154
|
entryPoints: [entryPath],
|
|
140
155
|
bundle: true,
|
|
@@ -144,6 +159,7 @@ async function dev() {
|
|
|
144
159
|
write: false,
|
|
145
160
|
});
|
|
146
161
|
let code = result.outputFiles[0].text;
|
|
162
|
+
// ā
Fix for react-dom/client exports
|
|
147
163
|
if (id === 'react-dom/client') {
|
|
148
164
|
code += `
|
|
149
165
|
import * as ReactDOMClient from '/@modules/react-dom';
|
|
@@ -156,16 +172,25 @@ async function dev() {
|
|
|
156
172
|
res.end(code);
|
|
157
173
|
}
|
|
158
174
|
catch (err) {
|
|
159
|
-
const
|
|
175
|
+
const e = err;
|
|
176
|
+
console.error(chalk_1.default.red(`ā Failed to load module ${id}: ${e.message}`));
|
|
160
177
|
res.writeHead(500);
|
|
161
|
-
res.end(`// Failed to resolve module ${id}: ${
|
|
178
|
+
res.end(`// Failed to resolve module ${id}: ${e.message}`);
|
|
162
179
|
}
|
|
163
180
|
});
|
|
164
|
-
// --- Serve /src files dynamically
|
|
181
|
+
// --- Serve /src files dynamically (auto extension fallback)
|
|
165
182
|
app.use(async (req, res, next) => {
|
|
166
183
|
if (!req.url || (!req.url.startsWith('/src/') && !req.url.endsWith('.css')))
|
|
167
184
|
return next();
|
|
168
|
-
const
|
|
185
|
+
const rawPath = decodeURIComponent(req.url.split('?')[0]);
|
|
186
|
+
let filePath = path_1.default.join(appRoot, rawPath);
|
|
187
|
+
const possibleExts = ['', '.tsx', '.ts', '.jsx', '.js'];
|
|
188
|
+
for (const ext of possibleExts) {
|
|
189
|
+
if (await fs_extra_1.default.pathExists(filePath + ext)) {
|
|
190
|
+
filePath += ext;
|
|
191
|
+
break;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
169
194
|
if (!(await fs_extra_1.default.pathExists(filePath)))
|
|
170
195
|
return next();
|
|
171
196
|
try {
|
|
@@ -174,15 +199,13 @@ async function dev() {
|
|
|
174
199
|
return res.end(transformCache.get(filePath));
|
|
175
200
|
}
|
|
176
201
|
let code = await fs_extra_1.default.readFile(filePath, 'utf8');
|
|
177
|
-
//
|
|
202
|
+
// Rewrite bare imports ā /@modules/*
|
|
178
203
|
code = code
|
|
179
204
|
.replace(/\bfrom\s+['"]([^'".\/][^'"]*)['"]/g, (_match, dep) => `from "/@modules/${dep}"`)
|
|
180
205
|
.replace(/\bimport\(['"]([^'".\/][^'"]*)['"]\)/g, (_match, dep) => `import("/@modules/${dep}")`);
|
|
181
|
-
|
|
182
|
-
for (const p of plugins) {
|
|
206
|
+
for (const p of plugins)
|
|
183
207
|
if (p.onTransform)
|
|
184
208
|
code = await p.onTransform(code, filePath);
|
|
185
|
-
}
|
|
186
209
|
const ext = path_1.default.extname(filePath);
|
|
187
210
|
let loader = 'js';
|
|
188
211
|
if (ext === '.ts')
|
|
@@ -201,12 +224,13 @@ async function dev() {
|
|
|
201
224
|
res.end(result.code);
|
|
202
225
|
}
|
|
203
226
|
catch (err) {
|
|
204
|
-
const
|
|
227
|
+
const e = err;
|
|
228
|
+
console.error(chalk_1.default.red(`ā ļø Transform failed: ${e.message}`));
|
|
205
229
|
res.writeHead(500);
|
|
206
|
-
res.end(`// Error: ${
|
|
230
|
+
res.end(`// Error: ${e.message}`);
|
|
207
231
|
}
|
|
208
232
|
});
|
|
209
|
-
// --- Serve index.html
|
|
233
|
+
// --- Serve index.html + overlay + HMR client
|
|
210
234
|
app.use(async (req, res, next) => {
|
|
211
235
|
if (req.url !== '/' && req.url !== '/index.html')
|
|
212
236
|
return next();
|
|
@@ -261,7 +285,7 @@ async function dev() {
|
|
|
261
285
|
console.log(chalk_1.default.yellow(`š Changed: ${file}`));
|
|
262
286
|
transformCache.delete(file);
|
|
263
287
|
for (const p of plugins) {
|
|
264
|
-
p.onHotUpdate?.(file, {
|
|
288
|
+
await p.onHotUpdate?.(file, {
|
|
265
289
|
broadcast: (msg) => broadcaster.broadcast(msg),
|
|
266
290
|
});
|
|
267
291
|
}
|
|
@@ -270,7 +294,7 @@ async function dev() {
|
|
|
270
294
|
path: '/' + path_1.default.relative(appRoot, file).replace(/\\/g, '/'),
|
|
271
295
|
});
|
|
272
296
|
});
|
|
273
|
-
// š
|
|
297
|
+
// š Start server
|
|
274
298
|
server.listen(port, async () => {
|
|
275
299
|
const url = `http://localhost:${port}`;
|
|
276
300
|
console.log(chalk_1.default.cyan.bold('\nš React Client Dev Server'));
|