挑战21天手写前端框架 day14 重启 node 服务

简介: 挑战21天手写前端框架 day14 重启 node 服务

image.png


昨天我们遗留了一个问题,在 malita dev 启动之后,修改配置之后,虽然页面有重新加载,但是配置数据的变更并没有被真正的覆盖到原来的逻辑,原因是我们仅仅重启了我们的浏览器端,但是并没有重启我们的服务端。


希望朋友们能够牢记这个问题,时刻提醒自己你当前编写的代码,最终是运行在服务端还是浏览器端,是编译时还是运行时,这个会让我们的框架在后续开发调试中减少非常多的异常,比如在服务端用 window 对象之类的。



服务端重启

常规的服务端重启,会采用 kill 子进程再重新启动的方式,如

import { fork } from 'child_process';
const run = ({scriptPath})=>{
  const child = fork(scriptPath);
  child.on('message', (data: any) => {
    if (data === 'RESTART') {
      child.kill();
      run({ scriptPath });
    }
    process.send?.(data);
  });
  return child;
}
复制代码


这有个问题,我们重启服务的时候,要重启所有的流程。

通过分析,我们的项目中,其实修改配置文件促发的重启,我们只是要重新构建主入口和html,因此我们将这两个生命周期单独提取出来。

const buildMain = async ({ appData }: { appData: AppData }) => {
        // 获取用户数据
        const userConfig = await getUserConfig({
            appData, sendMessage
        });
        // 获取 routes 配置
        const routes = await getRoutes({ appData });
        // 生成项目主入口
        await generateEntry({ appData, routes, userConfig });
        // 生成 Html
        await generateHtml({ appData, userConfig });
    }
复制代码


接下来解决就简单了,我们只要在监听到 REBUILD 的时候,重新执行一下 buildMain 就可以,这将会触发重新生成主入口文件,然后主入口文件变更,会触发 esbuild 重新构建,向浏览器端发送 reload 事件,完成服务端和客户端的同时重启。


修改 getUserConfig,将 const malitaServe = createServer(app); 传进去

const userConfig = await getUserConfig({
-    appData, sendMessage
+    appData, malitaServe
});
复制代码


我们主要是使用它来触发事件

onRebuild: (err, res) => {
        if (err) {
            console.error(JSON.stringify(err));
            return;
        }
+        malitaServe.emit('REBUILD', { appData });
    }
复制代码


然后在 dev 中监听这个事件

malitaServe.on('REBUILD', async ({ appData }) => {
    await buildMain({ appData });
})
复制代码


编写完成之后,发现一个“奇怪”的表现,整个构建重启环节都没有问题,你可以尝试在每个环节中查看数据变化,都是正确的,包括 userConfig 但是实际页面并没有变化,主入口和 html 也重新构建了,但是结果却是错的。

config = require(path.resolve(appData.paths.absOutputPath, 'malita.config.js')).default;
复制代码


最终定位排查问题,是 require 的时候会读取缓存。我们把缓存删了,强制读取最新的文件内容。

const configFile = path.resolve(appData.paths.absOutputPath, 'malita.config.js');
delete require.cache[configFile];
config = require(configFile).default;
复制代码



效果演示

image.png

感谢阅读,由于我在网上搜索如何重启 node 服务,找到的都不是我要的东西,我想要的是“如何重启”搜出来的都是“如何保活”,所以我就把这内容当作单独的一篇文章了。

预告:明天的内容是 Proxy 代理和本地 Mock 数据


源码归档

目录
相关文章
|
5天前
|
JavaScript 前端开发 API
Node.js在前端的妙用:打造更出色的Web体验
Node.js在前端的妙用:打造更出色的Web体验
176 5
|
5天前
|
Web App开发 JavaScript 前端开发
从脚手架开始学前端 【第3期】Node.js环境搭建(CentOS 7)
从脚手架开始学前端 【第3期】Node.js环境搭建(CentOS 7)
49 0
|
5天前
|
Web App开发 JavaScript 前端开发
从脚手架开始学前端 【第2期】Node.js环境搭建(windows)
从脚手架开始学前端 【第2期】Node.js环境搭建(windows)
43 0
|
5天前
|
Kubernetes 应用服务中间件 Docker
Kubernetes学习-集群搭建篇(二) 部署Node服务,启动JNI网络插件
Kubernetes学习-集群搭建篇(二) 部署Node服务,启动JNI网络插件
|
5天前
|
SQL 前端开发 JavaScript
前端vite+vue3结合后端node+koa——实现代码模板展示平台(支持模糊搜索+分页查询)
前端vite+vue3结合后端node+koa——实现代码模板展示平台(支持模糊搜索+分页查询)
41 4
|
5天前
|
存储 缓存 NoSQL
node实战——koa给邮件发送验证码并缓存到redis服务(node后端储备知识)
node实战——koa给邮件发送验证码并缓存到redis服务(node后端储备知识)
25 0
|
5天前
|
前端开发 JavaScript 内存技术
Node-前端模块化
Node-前端模块化
24 0
Node-前端模块化
|
6月前
|
JavaScript 前端开发 数据库
前端常见知识点汇总(ES6,Vue,axios,Node.js,npm,webpack)-3
前端常见知识点汇总(ES6,Vue,axios,Node.js,npm,webpack)
53 0
|
5天前
|
JSON JavaScript 前端开发
Node.js:前端开发的后端利器
Node.js作为一种运行在服务器端的JavaScript环境,为前端开发者打开了后端开发的大门。它以其高效的事件驱动、非阻塞I/O模型以及强大的npm生态,使得前端开发者能够轻松构建服务器端应用,实现前后端的全栈开发。本文将探讨Node.js的核心优势、应用场景以及在前端开发中的重要性。
|
5天前
|
Windows
node搭建本地https和wss服务
node搭建本地https和wss服务
30 0