UNPKG

3.93 kBJavaScriptView Raw
1/*!
2 * Module dependencies.
3 */
4var Definition = require('./definition')
5 , Schema = require('mongoose').Schema
6;
7
8
9/**
10 * Modeler constructor
11 *
12 * @param {Array} dbs
13 * @api public
14 */
15function Modeler( dbs){
16 this.dbs = {};
17 for( var i in dbs){
18 this.dbs[ dbs[ i].name] = dbs[ i];
19 }
20 this.definitions = {};
21};
22
23
24/**
25 * Populate list of Mongoose Models from Schemas and
26 * register them with the defined database connections.
27 *
28 * @param {Array} defs
29 * @param {Boolean} [autoload]
30 * @api public
31 * @method populate
32 * @memberOf Modeler
33 */
34Modeler.prototype.populate = function(defs, autoload){
35 var def, d, i;
36 for( i in defs){
37 def = defs[ i];
38 if( !this.definitions[ def.path]){
39 d = new Definition(
40 def.name,
41 def.schema,
42 def.database,
43 def.dependencies
44 );
45 this.definitions[ d.path] = d;
46 }
47 }
48 if( autoload){
49 for( i in this.definitions){
50 this._load( this.definitions[ i]);
51 }
52 }
53};
54
55/**
56 * Retrieve a specific Model instance from a database connection.
57 *
58 * @param {String} name Model name
59 * @param {String} db database anme
60 * @param {Boolean} [autoload]
61 * @return {Boolean|mongoose.Model}
62 * @api public
63 * @method find
64 * @memberOf Modeler
65 */
66Modeler.prototype.find = function(name, db, autoload){
67 if( !name||!db) throw new Error('Missing parameter(s).');
68 var dbo = this.dbs[ db], path = db+'.'+name, def;
69 if( dbo){
70 if( dbo.models[ name]){
71 return dbo.models[ name];
72 }else if( this.definitions[ path]&&autoload) {
73 return this._load( this.definitions[ path]);
74 }
75 }else if( autoload){
76 throw new Error('Database ['+db+'] is not connected or defined. Requested by Model ['+name+']');
77 }
78 return false;
79};
80
81
82/**
83 * Retrieve a specific Model instance from a database connection.
84 *
85 * @param {String} name Model name
86 * @param {String} db database anme
87 * @param {Boolean} [autoload]
88 * @return {Boolean|mongoose.Model}
89 * @api public
90 * @method find
91 * @memberOf Modeler
92 */
93Modeler.prototype.require = function(name, db){
94 if( !name||!db) throw new Error('Missing parameter(s).');
95 return this.find(name, db, true);
96};
97
98
99/**
100 * Retrieve a specific Model instance from a database connection.
101 *
102 * @param {Definition} def Schema Definition
103 * @api private
104 * @method _load
105 * @memberOf Modeler
106 */
107Modeler.prototype._load = function(def){
108 if( !def) return false;
109 var db = this.dbs[ def.database];
110 if( !db) throw new Error('Database ['+def.database+'] is not connected or defined. Requested by Model ['+def.name+']');
111 if( !this.find( def.name, def.database)){
112 if( def.hasDependencies()){
113 this._resolve( def);
114 }
115 if( !def.schema){
116 def.create( this);
117 }
118 if( def.schema instanceof Schema){
119 db.model( def.name, def.schema);
120 }else {
121 throw new Error('Undefined or Invalid Schema object for ['+def.name+']');
122 }
123 }
124 return db.models[ def.name];
125};
126
127
128/**
129 * Resolve Model dependencies.
130 *
131 * @param {Definition} def Schema Definition
132 * @api private
133 * @method _resolve
134 * @memberOf Modeler
135 */
136Modeler.prototype._resolve = function( def){
137 for( var i in def.dependencies){
138 var dep = def.dependencies[i]
139 , p = dep.split('.')
140 , db = p[0] , name = p[1]
141 ;
142 if( !this.find( name, db)){
143 this._load( this.definitions[ dep]);
144 }
145 }
146};
147
148
149
150
151/*!
152 * Module exports.
153 */
154
155
156/**
157 * Factory method for creating Modeler instances.
158 *
159 * @param {Array} dbs Mongoose Database connections
160 * @param {Array} degs Schema Definitions
161 * @param {Boolean} [autoload]
162 * @api public
163 */
164module.exports = function(dbs, defs, autoload){
165
166 var modeler = new Modeler( dbs);
167 if( defs){
168 modeler.populate( defs, autoload);
169 }
170 return modeler;
171};
172
173
174
175/**
176 * Modeler export
177 */
178module.exports.Modeler = Modeler;
179
180
181/**
182 * Definition export
183 */
184module.exports.Definition = Definition;
\No newline at end of file