是否可以使用 express.js 清除 node.js 需要缓存?
Posted
技术标签:
【中文标题】是否可以使用 express.js 清除 node.js 需要缓存?【英文标题】:Is it possible to clear node.js require cache using express.js? 【发布时间】:2020-07-19 15:25:21 【问题描述】:我为自己编写了 node.js 小应用程序,它在处理请求之前使用小 js 代码清除 require 缓存:
let clearCache
if (process.env.NODE_ENV === 'development')
const cache = require
clearCache = (except) =>
for (let key in cache)
if (!except.includes(key) && key.indexOf('/node_modules/') === -1)
delete cache[key]
else
clearCache = () =>
const createServer = require('http')
const persistentPaths = ['/path/to/my/db/file']
createServer((req, res) =>
clearCache(persistentPaths)
require('./handleRequest')(req, res)
).listen(3000, () => )
我相信这是在开发中使用应用的最有效方式。
当我更改代码时,它会立即生效,这对我来说很好。
现在我想使用 express.js,但似乎无法使用这种方法。
好的,看来这是一个自我回答的问题,我需要使用 nodemon。
但我真的不想使用监视所有文件并重新启动整个服务器的工具。恐怕会慢很多。
在我的示例中,您可以看到我重新加载了除 db 文件之外的文件,因此我正在开发的应用程序仅连接到数据库一次并保持该连接。如果使用 nodemon 应用程序还需要加载所有 node_modules 代码,每次代码更改时都与 db 建立新连接,也许每次都会连接到 postgres 和 redis。
问题是:我不能这样做,有没有解决方案为 express.js 重新加载模块?
【问题讨论】:
【参考方案1】:您无需编写一个实用程序。你可以使用像 chokidar 这样的模块。可以同时指定目录和忽略。
您可以在回调手表时重新加载。
来自 wiki 的示例::https://github.com/paulmillr/chokidar
const chokidar = require("chokidar");
// Full list of options. See below for descriptions.
// Do not use this example!
chokidar.watch("file",
persistent: true,
ignored: "*.txt",
ignoreInitial: false,
followSymlinks: true,
cwd: ".",
disableGlobbing: false,
awaitWriteFinish:
stabilityThreshold: 2000,
pollInterval: 100,
,
ignorePermissionErrors: false,
atomic: true, // or a custom 'atomicity delay', in milliseconds (default 100)
);
// One-liner for current directory
chokidar.watch(".").on("all", (event, path) =>
// Reload module here.
);
【讨论】:
Chokidar 会产生开销:它是单独的过程,必须查看许多文件,在代码编辑和重新加载之间增加了额外的延迟,这就是我不想使用它的原因 感谢您的回复,但是,您没有展示如何使用 chokidar 重新加载 express 应用代码,仅展示如何使用 chokidar 重新加载很容易再次要求。手表就是这样工作的,拉或推。在这里推送是不可能的,你必须拉上特定的时间戳。您可以在配置中降低频率。 这里是 chokidar 代码,它不会为每个文件创建线程。你在哪里看到节点 js 中的线程?? github.com/paulmillr/chokidar/blob/master/lib/nodefs-handler.js node js 是单线程框架。所以你不要在nodejs代码中创建一个线程。除非你使用工作模块。这里没用过。 但我没有使用word thread,只使用整个chokidar的过程。我看过一篇文章,其中一个节点实例中有 chokidar,它正在发送请求以更新快速节点实例中的代码。知道了,所以在您的示例中,chokidar 和 express 应用程序将在同一进程中运行。在您的示例中,如何在手表回调中重新加载快速应用程序?需要每次都会创建服务器的“server.js”文件吗?并且在要求之前需要杀死正在运行的服务器?或者怎么做?【参考方案2】:做到了!如果你能分享你的想法,我会很高兴。
因为我只能用谷歌搜索 nodemon 和 chokidar 解决方案,也许我在做一些奇怪的事情,这是我的解决方案:
server.ts:
import express from 'express'
const app = express()
const port = 3000
app.listen(port, () =>
console.log(`Example app listening at http://localhost:$port`)
)
if (process.env.NODE_ENV === 'development')
const cache = require
const persistentFiles: string[] = []
const clearCache = (except: string[]) =>
for (let key in cache)
if (!except.includes(key) && key.indexOf('/node_modules/') === -1)
delete cache[key]
app.use((req, res, next) =>
clearCache(persistentFiles)
const router = require('config/routes')
router.handle(req, res, next)
)
else
const router = require('config/routes')
app.use(router.handle)
还有 routes.ts:
import Router, Request, Response from 'express'
export const router = Router()
router.get('/', function (req: Request, res: Response)
res.send('Hello world')
)
用法:NODE_ENV=development NODE_PATH=src node src/server.js
(我的IDE在编辑的时候把ts编译成js放在那里,如果你使用VS代码可能会更复杂,我猜)
【讨论】:
以上是关于是否可以使用 express.js 清除 node.js 需要缓存?的主要内容,如果未能解决你的问题,请参考以下文章
我可以在 Node.js/Express 中动态导入 TypeScript 模块吗?