2015-06-29 10 views
7

Ich bin jetzt für eine Weile fest stecken, versuchen, Einheitstest einrichten und runnnning."Fehler: Mismatched anonymous define()" mit Karma + RequireJS + Jasmine

Ich habe ein AngularJS-Frontend geladen mit RequireJS und r.js für die Produktion optimiert, so ist es alles schön in einer einzigen Datei. Das funktioniert!

Was nicht funktioniert, ist die Durchführung der Komponententests. Das ist bisher nichts Besonderes, nur einen Starter aus einem Tutorial kopiert.

tests/user/user.test.js:

define(['angular', 'angular-mocks', 'app'], function(angular, app) { 
    describe('Unit: UserController', function() { 
    beforeEach(module('user.app')); 

    it('should do something', function() { 
     console.log('did it'); 
    }); 
    }); 
}); 

Dann habe ich ein karma.conf.js:

module.exports = function(config) { 
    config.set({ 
    logLevel: config.LOG_DEBUG, 
    basePath: './', 

    files: [ 
     // r.js'd app files 
     {pattern: 'dist/app.js', included: false}, 
     // the tests 
     {pattern: 'tests/**/*.test.js', included: true}, 
    ], 

    excluded: ['tests/main.test.js'] 

    frameworks: ['jasmine', 'requirejs'], 

    browsers: ['PhantomJS'], 

    plugins: [ 
     'karma-jasmine', 
     'karma-junit-reporter', 
     'karma-phantomjs-launcher', 
     'karma-requirejs' 
    ], 

    }); 
}; 

A main.test.js:

var allTestFiles = []; 
var TEST_REGEXP = /(spec|test)\.js$/i; 

var pathToModule = function(path) { 
    var returnValue = path.replace(/^\/base\//, '').replace(/\.js$/, ''); 
    return returnValue; 
}; 

Object.keys(window.__karma__.files).forEach(function(file) { 
    if (TEST_REGEXP.test(file)) { 
    // Normalize paths to RequireJS module names. 
    allTestFiles.push(pathToModule(file)); 
    } 
}); 

require.config({ 
    baseUrl: '/base', 

    paths: { 
    'angular-mocks': 'node_modules/angular-mocks/angular-mocks', 
    'app': 'dist/app', 
    }, 

    deps: allTestFiles, 

    callback: function() { 
    console.log('load complete'); 
    window.__karma__.start(); 
    }, 
}); 

Und schließlich ein gulp Aufgabe:

var gulp = require('gulp'); 
var karma = require('karma').server; 

gulp.task('unit-test', function(done) { 
    karma.start({ 
    configFile: __dirname + '/karma.conf.js', 
     singleRun: true 
    }, function() { done(); }); 
} 

Hier und da habe ich einige Log-Ausgaben hinzugefügt und es zeigt, dass die Dateien geladen sind.

Aber ich bin stecken in Error: Mismatched anonymous define() in der tests/user/user.test.js und ich sehe nicht, was falsch ist. Hier ist der Ausgang: http://pastebin.com/evJPj9B3

Wenn ich das Gerät Testmodul wie

define('namedtestorso', ['angular', 'angular-mocks', 'app'], function(angular, app) { 
    ... 

nennen ... Ich erhalte keinen Fehler mehr, sondern die Tests werden nicht ausgeführt. Da alle Beispiele, an die ich mich erinnern kann, es als anonyme Definition verwenden, nehme ich an, dass die Benennung hier nicht korrekt ist. In diesem Fall wird jedoch die Protokollausgabe ausgeführt, die zeigt, dass der Konfigurationsrückruf von main.test.js zweimal ausgeführt wird. (Ist das ein Hinweis für etwas?)

Wäre toll, wenn jemand eine Idee hat, wie man es repariert/es zum Laufen bringt oder sogar weiter geht, um herauszufinden, was falsch ist. Danke im Voraus!

Antwort

9

Ich habe jetzt läuft es so hier meine Lösung verlassen:

Ich glaube, ich besser, ein bisschen jetzt verstanden, wie karma Werke (pls erklären mir, wenn ich falsch liege) und fand so, was ich tun musste.

Es scheint alles um Dateien in die karma.conf.js setzen, so dass sie für die main.test.js geladen werden verfügbar sind. Andernfalls sind sie außerhalb des "Kontexts" und können nicht aufgerufen werden. Stellen Sie jedoch sicher, dass das Flag included auf false gesetzt wird.

Änderungen an der karma.conf.js:

files: [ 
    ... 
    // Also included these dependencies. All the others are minified in the 
    // app.js but if you don't do that, also include all project deps like 
    // AngularJS etc. 
    { pattern: 'node_modules/jasmine-core/lib/jasmine-core/boot.js', included: false }, 
    { pattern: 'node_modules/angular-mocks/angular-mocks.js', included: false}, 

    // Then I had an error in my pattern ('tests/**/*.test.js') 
    // Only the `main.test.js` is supposed to be included! 
    { pattern: 'tests/user/user.test.js', included: false } 
    { pattern: 'tests/main.test.js', included: true } 
    ... 

Wenn ich richtig Karma eine HTML-Datei und Dateien mit included: true über Script-Tags geladen werden erstellt. Deshalb ist es wichtig, wenn Sie RequireJS verwenden, include auf false zu setzen, da Sie andernfalls die Error: Mismatched anonymous define() erhalten. Das macht jetzt Sinn für mich.

Nach der Lösung dieses Problems gab es einige andere mit Modulen nicht gefunden. Da ich den RequireJS-Optimierer verwendet habe, musste ich alle meine Module den Hauptdateien app.js zuordnen, so dass RequireJS, wenn die Test-JS-Dateien ein bestimmtes Modul erforderten, sicherstellen konnte, dass es geladen wurde (oder wird).

So landete ich den paths Abschnitt in main.test.js Wechsel auf:

paths: { 
    // Added these for example 
    'angular': '../dist/app', 
    'angular-ui-router': '../dist/app', 
    // (and also my project modules) 
    ... 

Rechts, die ein bisschen hacky scheint. In der Zwischenzeit, nachdem ich dieses Problem gelöst habe, ändere ich auch meinen Arbeitsablauf, um den Komponententest für die Dev-Dateien auszuführen und mich auf die anderen Tools zu verlassen, um ordnungsgemäß zu funktionieren (und wenn Probleme nicht durch e2e-Tests aufgefangen werden).

Hoffe es hilft anderen in meiner Situation!

0

Genau, wenn Sie vor Ort gehen diese Fehlerzustände requirejs, wenn Sie irgendein Skript-Tag enthalten sind, in HTML bedeutet dies, html von Karma bereitgestellt

So in karma.conf.js, wenn Sie Dateien wie beinhalten: Dateien [ ‚/base/src/scripts/xyz.js‘] meiner Meinung nach ist es als Skript-Tag hinzugefügt und u halten auf immer Fehler: Nicht übereinstimm anonym definieren() -Modul

try Musterbeispiel: { Muster: '/base/src/scripts/xyz.js', enthalten: false} verhindert das Hinzufügen von js in Skript-Tags

Verwandte Themen