Comment tester les fonctions JavaScript "normales" (non spécifiques aux noeuds) avec Mocha?

Cela semble comme il devrait être extrêmement simple; cependant, après deux heures de lecture et d'essais et d'erreurs, sans succès, je suis d'admettre la défaite et de vous demander de vous les gars!

je suis en train d'utiliser MokaDevrait.js pour tester certaines fonctions JavaScript, mais j'ai des problèmes de cadrage. Je l'ai simplifié jusqu'aux cas les plus simples, mais je ne peux pas le faire fonctionner.

j'ai un fichier nommé functions.js, qui seulement contient le code suivant:

function testFunction() {
    return 1;
}

Et mon tests.js (situé dans le même dossier) contenu:

require('./functions.js')

describe('tests', function(){
    describe('testFunction', function(){
        it('should return 1', function(){
            testFunction().should.equal(1);
        })
    })
})

Ce test échoue avec un ReferenceError: testFunction is not defined.

je peux voir pourquoi, parce que la plupart des exemples que j'ai trouvés attachent des objets et des fonctions au noeud global objet ou de les exporter à l'aide de module.exports - mais l'utilisation de l'une ou l'autre de ces approches signifie que mon code de fonction lancerait des erreurs dans une situation de navigateur standard, où ces objets ne exister.

alors comment puis-je accéder aux fonctions autonomes qui sont déclarées dans un fichier de script séparé de mes tests, sans utiliser la syntaxe spécifique au noeud?

45
demandé sur Mark Bell 2012-04-18 10:30:58

3 réponses

require('./functions.js')

cela ne fait rien puisque vous n'exportez rien. Ce que vous attendez, c'est que testFunction est disponible à l'échelle mondiale, essentiellement la même que

global.testFunction = function() {
    return 1;
}

Vous vous ne pouvez pas contourner le mécanisme export/globals. C'est la façon dont le noeud a été conçu. Il n'y a pas de contexte global partagé implicite (comme window sur un navigateur). Chaque variable "globale" d'un module est piégée dans son contexte.

Vous devez utiliser module.exports. Si vous avez l'intention de partagez ce fichier avec un navigateur, il y a des moyens de le rendre compatible. Pour un rapide hack il suffit de ne window.module = {}; jQuery.extend(window, module.exports) dans le navigateur, ou if (typeof exports !== 'undefined'){ exports.testFunction = testFunction } pour le nœud.

15
répondu Ricardo Tomasi 2012-04-18 06:54:27

grâce aux autres réponses ici, j'ai des choses qui fonctionnent.

une chose qui n'a pas été mentionnée cependant-peut-être parce que C'est de notoriété publique parmi les noteurs-était que vous devez assigner le résultat du require appeler une variable, de sorte que vous pouvez vous y référer lorsque vous appelez vos fonctions exportées depuis la suite de test.

Voici mon code complet, pour le futur référence:

functions.js:

function testFunction () {
    return 1;
}

// If we're running under Node, 
if(typeof exports !== 'undefined') {
    exports.testFunction = testFunction;
}

tests.js:

var myCode = require('./functions')

describe('tests', function(){
    describe('testFunction', function(){
        it('should return 1', function(){
            // Call the exported function from the module
            myCode.testFunction().should.equal(1);
        })
    })
})
24
répondu Mark Bell 2012-04-18 12:34:47

si vous voulez rendre n'importe quel module disponible via require, vous devez utiliser

module.exports

comme vous le savez ;)

il y a une solution si vous voulez utiliser un module dans le noeud et dans le navigateur en faisant ceci

function testFunction() { /* code */ }

if (typeof exports !== 'undefined') {
   exports.testFunction = testFunction
}

en faisant cela vous pourrez utiliser le fichier dans le navigateur et dans l'environnement de noeud

6
répondu drinchev 2012-04-18 06:55:13