【egg】编写cotroller单元测试的时候,如何保证app上挂载的插件都加载完成了?比如redis或者sequelize
发布于 4 年前 作者 Redtwodog 5151 次浏览 来自 问答

第一次写单元测试,发现一旦请求进入到service的数据库操作就会报 app.model is undefind. 排查之后发现,egg-mock的app上 每个 plugin 的时序挂载不是一致的,比如一些纯函数的插件,就是立即生效的,但是redis 和 mysql这种需要连接数据库的就不是。 所以看了很长时间文档也没有找到如何正确的写这部分的测试方法,试了下把测试代码放在 after的钩子里好像也不行 。 请大佬为我解惑啊。

	const assert = require('assert');
	const mock = require('egg-mock');
	describe('test/app/controller/app.test.js',()=>{
		let app;
		before(() => {
		  app = mock.app();
		  return app.ready();
		});
		describe('GET /app/list', async ()=>{
			it('should status 200 and get body', async ()=>{
				app.mockCsrf();
				const result = await app.httpRequest()
					.get('/app/list?page=1&page_size=10')
				assert(app.model);
				// 发现   上面断言失败了
			    assert(result.status === 200);
			})
		})
	}

-----------------------------service------------------------------------------------

    async List({
        page,
        page_size,
        id,
        name,
    }){
        const {app} = this;
        const query = {
            offset:Number((page-1)*page_size),
            limit:Number(page_size),
            order: [[ 'm_time', 'desc' ]],
            where:{
                deleted:0
            },
            include:{
                model:app.model.AppTask
            }
        };
		......省略
        const result = await app.model.App.findAndCountAll(query);       
        return result;
    }

错误

     AssertionError [ERR_ASSERTION]:   # test\app\controller\app.test.js:18       

  	assert(app.model)
         |   |
         |   undefined
         MessengerApplication{_events:#Object#,_eventsCount:5,_maxListeners:undefined,options:#Object#,closed:false,ready:#function#,_agent:#Agent#,_app:#MessengerApplication#}
5 回复

/(ㄒoㄒ)/~~崩溃了。到底怎么搞啊。@天猪 救我啊。 为什么就正好egg-redis 和 egg-sequelize 没有在mock的app上啊。 难道数据库操作要mock掉?

楼主可以看看这个,或许能解决你的问题,我们团队也遇到过类似的问题 https://www.npmjs.com/package/e-promise

我们的策略是,允许程序立即调用,等待连接成功的时候,立即发送

可以 await 一下 app.ready();

最简单的方式,看下 egg-sequelize 和 egg-redis 自身的单测怎么写的

回到顶部