Require renvoie un objet vide


126

J'ai un dossier, qui a index.js et quelques modèles (classes) index.js

module.exports = {
   Book : require('./book'),
   Author : require('./author')
}

book.js

var Author = require('./author')
var Book = models.ActiveRecord.extend({
    schema : {
        belongsTo : {
            author : Author
        }
    }
})
module.exports = Book

author.js

var Book = require('./book')
var Author = models.ActiveRecord.extend({
    schema : {
        hasMany : {
            author : Book
        }
    }
})

module.exports = Author

Le problème est que la classe Author ne semble pas trouver le livre! C'est juste un objet vide. Cependant, si je change les exportations dans index.js, en mettant Book après Author - cela fonctionne, mais l'autre modèle cesse de fonctionner.

Je ne veux pas faire de hacks pour que ça marche.


4
Author.js a besoin de Book.js pour fonctionner, et Book.js a besoin de Author.js pour fonctionner? Supprimez la dépendance circulaire.
— Philipp Gayret

1
De quel objet ActiveRecord s'agit-il? D'où cela vient-il?
— BT

Réponses:


208

C'est parce que vous avez une dépendance circulaire. Node.js gère cela d'une manière très spécifique:

  1. Le premier module se charge et s'exécute (dans ce cas, book.js). Il ( book.js) chargera et exécutera le deuxième module ( author.js) quand il ( book.js) nécessitera l'autre ( author.js)

  2. Lorsque le deuxième module ( author.js) est chargé et exécuté, il ( author.js) nécessite le premier module ( book.js) mais il ( author.js) recevra un objet partiellement rempli - quel que soit le nombre de choses qui ont été définies sur les exportations dans book.js avant qu'il ne soit nécessaire, author.js sera être dans cet objet

  3. Après avoir book.jsété complètement exécuté, l'objet author.jsobtenu require('./book')sera l' book.jsobjet module complet

Pour plus d'informations, voici la documentation: http://nodejs.org/api/modules.html

S'il est possible d'ajouter dynamiquement ce schéma à l'un de ces objets ActiveRecord, c'est une façon de résoudre ce problème. C'est en fait une situation délicate. En fait, même sans le système de modules, cela vous poserait des problèmes. Si vous mettez tout ce code dans un seul fichier, comment le feriez-vous fonctionner?


1
Je sais que vous ne devriez pas tout mettre dans un seul fichier, mais je dis juste expérimenter comme ça. Ce que je veux dire, c'est que ce n'est pas le système de modules de node.js qui pose le problème ici, c'est le code lui-même.
— BT

Et en fait, Java a les mêmes problèmes avec les dépendances circuclaires - c'est un problème que n'importe quel langage peut avoir. Si tout ce dont vous avez besoin est une référence à votre partenaire de dépendance circulaire, javascript peut le faire aussi facilement que java. Cependant, ici, vous essayez d'utiliser l'objet avant qu'il ne soit construit (dans l'extension)
— BT

Ouais, en fait maintenant je l'ai compris. Jamais venu à l'esprit. Donc, il n'y a qu'une seule façon - de l'ajouter dynamiquement, je suppose. Ou en passant un nom de modèle sous forme de chaîne. Merci pour votre réponse!
— user3677173

18
Je recommande vivement Madge pour le débogage de ce type de problèmes dans des cas plus complexes (c'est-à-dire avec plus de fichiers). Une fois installé, vous pouvez l'utiliser madge -c <app entry point>pour détecter les dépendances circulaires.
— schu34

7
Merci. Assez douloureux qu'il ne lance même pas d'erreur mais renvoie simplement un objet vide.
— Robert Oschler
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.