Fastify插件依赖问题:路由前注册MySQL失败引发报错
Fastify中MySQL插件未挂载导致路由报错的问题解决
问题原因
- 插件并行注册与嵌套异步注册的冲突:Fastify默认并行执行所有顶级
register调用,你的db.js插件内部嵌套注册了@fastify/mysql,但未等待该插件完成初始化就调用了done(),导致payments路由插件加载时,fastify.mysql还未挂载到实例上。 - 插件完成时机错误:封装插件必须确保内部所有嵌套注册的插件完成后再触发
done(),否则外部插件会先于内部依赖插件完成初始化。
解决方案
方案1:修正DB插件的初始化逻辑
将db.js改为异步插件,等待内部MySQL插件注册完成后再完成自身初始化:
module.exports = async function (fastify, options) { await fastify.register(require('@fastify/mysql'), { connectionString: 'mysql://root:password@localhost/boodil' }) }
也可以使用回调方式实现:
module.exports = function (fastify, options, done) { fastify.register(require('@fastify/mysql'), { connectionString: 'mysql://root:password@localhost/boodil' }, done) }
方案2:声明插件依赖关系
在Server.js中给插件命名并声明依赖,确保payments插件在db插件完全初始化后再加载:
const fastify = require('fastify')({ logger: true }) fastify.register(require('./config/db'), { name: 'db-plugin' }) fastify.register(require('./routes/payments'), { dependsOn: 'db-plugin' }) const PORT = 2000 const start = async () => { try { await fastify.listen({ port: PORT }) } catch (e) { fastify.log.error(e) process.exit(1) } } start()
此方案需配合方案1中db.js的修正,确保db插件等待MySQL注册完成。
额外修正:路由参数格式错误
/get-transaction:id的参数格式不符合Fastify规范,动态参数需放在路径分隔符后,正确写法为/get-transaction/:id,否则无法解析req.params.id:
fastify.get('/get-transaction/:id', (req, reply) => { fastify.mysql.query( 'SELECT * FROM transactions where id = ?', [req.params.id], function onResult(err, result) { reply.send(err || result) } ) })
内容的提问来源于stack exchange,提问作者Dally
相关产品推荐
相关产品推荐

