【问题标题】:Running tests .mjs / ESM on Node using Jasmine or any other alternative使用 Jasmine 或任何其他替代方法在 Node 上运行测试 .mjs / ESM
【发布时间】:2017-12-15 12:38:35
【问题描述】:

由于--experimental-modules CLI 开关(即node --experimental-modules),我的基于Node 的项目是使用Node 上的本机ES 模块支持实现的。

显然,当我使用 Jasmine node --experimental-modules ./node_modules/jasmine/bin/jasmine 运行规范时,我收到以下错误:

错误 [ERR_REQUIRE_ESM]: 必须使用 import 来加载 ES 模块

有没有可能在 Node 中使用 ES 模块来使用 Jasmine?

如果没有,是否有任何替代方法不要使用框架(例如,使用npm 脚本运行测试)?

【问题讨论】:

    标签: javascript node.js testing jasmine es6-modules


    【解决方案1】:

    这比我想象的要容易。

    这只是调用一个文件,你可以调用run.mjs,如下所示:

    node --experimental-modules ./run.mjs

    整个文件如下所示:

    jasmine.mjs:

    import Jasmine from "jasmine"
    import JasmineConsoleReporter from "jasmine-console-reporter"
    
    const jasmine = new Jasmine()
    jasmine.loadConfigFile( "./support/jasmine.json" )
    
    jasmine.env.clearReporters()
    jasmine.addReporter( new JasmineConsoleReporter( {
        colors: true,
        cleanStack: true,
        verbosity: 4,
        listStyle: 'indent',
        activity: false
    } ) )
    
    export default jasmine
    

    您可以在单独的文件中添加如下规格:

    import jasmine from './my-project/spec/jasmine.mjs'
    
    jasmine.env.describe('Foo', () => {
        jasmine.env.it('Bar', () => {
            // Expects, assertions...
        })
    })
    

    最后,您将运行 jasmine 并导入配置的 jasmine 实例和规范:

    import jasmine from './my-project/spec/jasmine.mjs'
    import someSpec1 from './my-project/spec/someSpec1.mjs'
    import someSpecN from './my-project/spec/someSpecN.mjs'
    
    someSpec1()
    someSpecN()
    
    jasmine.execute()
    

    【讨论】:

    • 你能提供更多关于你是如何工作的吗?我有相同的目标,使用类似的 jasmine-running mjs 文件仍然会产生原始错误。我还尝试覆盖Jasmine.prototype.loadSpecs 函数以使用动态import 而不是require,但这会静默失败(看起来还不支持动态导入)
    • @Dave 检查我更新的答案。其实我也有你的问题,但我忘了更新它:D
    • 感谢您的更新。我希望避免更改测试本身,所以在它得到适当支持之前,我一直使用汇总和源映射而不是单独使用 Jasmine。不理想,但至少意味着我的测试保持干净。很高兴知道如果我需要更改它是可能的!
    • @Dave 你可以保持它们干净导出describe 和其他将它们绑定到jasmine 的函数:export const describe = jasmine.env.describe.bind(this)
    • @Dave 更改模块加载系统并不是难事。问题是 ejs 模块异步加载。所以从jasmine.execute() 开始的整个流程需要重构为异步代码。这是合理的,但可能需要一些时间。这就是为什么您的修改静默失败以及解决方法最终需要单独调用规范而不是通过 jasmine 配置的原因。更好的解决方法是在 jasmine.execute() 之前解析配置,处理 *.mjs 文件,并将 *.js 文件留作常规加载。
    【解决方案2】:

    简化@Matias_Fidemraizer 的解决方案,只保留一个文件中的重要位:

    import glob from 'glob';
    import Jasmine from 'jasmine';
    
    const jasmine = new Jasmine();
    jasmine.loadConfigFile('tests/jasmine.json');
    
    // Load your mjs specs
    glob('**/*-test.mjs', function (er, files) {
        Promise.all(
            files
                // Use relative paths
                .map(f => f.replace('tests/specs/', './'))
                .map(f => import(f)
                    .catch(e => {
                        console.error('** Error loading ' + f + ': ');
                        console.error(e);
                        process.exit(1);
                    }))
        )
            .then(() => jasmine.execute());
    });
    

    然后执行它

    node --experimental-modules jasmine-run.mjs
    

    你会在日志中遇到一些问题,收到类似的消息

    [...] .split('\n') [...]

    该消息意味着您的 mjs 代码中有异常。

    你可以关注:https://github.com/jasmine/jasmine-npm/issues/150

    【讨论】:

    • 不错。另外,我对这个问题表示支持。
    猜你喜欢
    • 2012-11-16
    • 1970-01-01
    • 1970-01-01
    • 2015-07-19
    • 2011-09-01
    • 1970-01-01
    • 2011-09-04
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多