AdonisJS控制器导入lighthouse npm包报错求助
AdonisJS控制器导入Lighthouse包的问题解决方法
问题描述
在AdonisJS控制器中导入lighthouse包时遇到两类错误:
- 使用
require('lighthouse')导入时,抛出**"Invalid or unexpected token"**错误,但导入chrome-launcher无异常;注释掉lighthouse的导入语句后错误消失。 - 改用ESM的
import lighthouse from 'lighthouse'语法时,触发**"'import' and 'export' may appear only with 'sourceType: module'"**错误。
原代码如下:
const lighthouse = require('lighthouse'); const Launcher = require('chrome-launcher'); const User = use('App/Models/User'); const Mail = use('Mail'); const Company = use('App/Models/Company'); const Project = use('App/Models/Project'); const Task = use('App/Models/Task'); const Database = use('Database'); class ReportingController { async getLighthouse({ request }) { const { url } = request.only(['url']); const chrome = await Launcher.launch({ chromeFlags: ['--headless'] }); const options = { logLevel: 'info', output: 'json', onlyCategories: ['performance'], port: chrome.port, }; const runnerResult = await lighthouse(decodeURIComponent(url), options); await chrome.kill(); return { data: runnerResult }; } } module.exports = ReportingController;
问题原因
Lighthouse从v6.x版本开始默认采用ESM模块格式发布,而AdonisJS v4.x默认使用CommonJS模块系统,直接用require导入ESM模块会触发语法错误;强行用import又会因为项目未配置ESM运行环境报错。
解决方法
方法1:安装CommonJS兼容版本的Lighthouse
如果不想修改项目模块配置,可以降级安装Lighthouse v5.x(最后一个稳定的CommonJS版本):
npm install lighthouse@5.6.0 --save
安装完成后,原require导入语法可正常运行。
方法2:将控制器改为ESM格式
- 将控制器文件扩展名从
.js改为.mjs - 修改代码为ESM语法:
import lighthouse from 'lighthouse'; import Launcher from 'chrome-launcher'; import User from 'App/Models/User'; import Mail from 'Mail'; import Company from 'App/Models/Company'; import Project from 'App/Models/Project'; import Task from 'App/Models/Task'; import Database from 'Database'; class ReportingController { async getLighthouse({ request }) { const { url } = request.only(['url']); const chrome = await Launcher.launch({ chromeFlags: ['--headless'] }); const options = { logLevel: 'info', output: 'json', onlyCategories: ['performance'], port: chrome.port, }; const runnerResult = await lighthouse(decodeURIComponent(url), options); await chrome.kill(); return { data: runnerResult }; } } export default ReportingController;
- 在路由文件中引用控制器时添加
.mjs扩展名:
const ReportingController = use('App/Controllers/Http/ReportingController.mjs');
方法3:启用项目混合模块支持(推荐)
- 安装
esm模块以支持CommonJS项目导入ESM模块:
npm install esm --save
- 修改项目启动文件(通常为
server.js),在顶部添加:
require = require('esm')(module);
- 之后即可在控制器中使用
import语法导入Lighthouse,同时保留其他CommonJS语法不变。
内容的提问来源于stack exchange,提问作者AnthonyTB
相关产品推荐
相关产品推荐

