UNPKG

6.92 kBJavaScriptView Raw
1var _ = require("underscore");
2var cluster = require("cluster");
3
4module.exports = function(env, cb){
5
6 var config = env.config;
7 var path = require("path");
8 var fs = require("fs");
9
10 var _ = require("underscore");
11 var bulk = require("bulk-require");
12
13 var actual_do;
14
15 env.testSetup = [];
16 env.stops = [];
17
18 env.stop = function(cb){ env.helpers.chain(env.stops)(cb); };
19
20 env.getCached = function(target){
21 if(!target.__cached) { target.__cached = target.apply(env); }
22 return target.__cached;
23 };
24
25 env.structureLoader = function(name, setup, cb, cached){
26 var structureConfig = env.config.structures[name];
27 if(!structureConfig.path && !structureConfig.instances) return cb();
28
29 // REMOVE ME - nonsense
30 // if(!structureConfig) return cb(new Error("Cant find config: env.config.structures."+name + " structure "+name));
31
32 if(structureConfig.path){
33 var stagePath = path.join(env.config.rootDir, Array.isArray(structureConfig.path)?structureConfig.path[0]:structureConfig.path);
34 if(fs.existsSync(stagePath)) {
35 env.i[name] = bulk(stagePath, Array.isArray(structureConfig.path)?structureConfig.path[1]:["**/*.js", "**/*.coffee"]);
36 }
37 else{
38 env.i[name] = {};
39 }
40 }
41 else{
42 env.i[name] = {};
43 }
44
45
46 var initializers = [], structureInit;
47
48 env.i[name].do = env.i.do;
49
50
51 if(env.i[name].index) {
52 structureInit = env.i[name].index;
53 delete env.i[name].index;
54 }
55
56 if(structureInit) structureInit.call(env, function(err, postinit){
57 if(err) return cb(err);
58 if(postinit) go(function(err){
59 if(err) return cb(err);
60 postinit(cb);
61 });
62 else go(cb);
63 });
64 else go(cb);
65
66 function go(cb){
67 env.helpers.traverse(env.i[name], function(target, nodeName, parent, path){
68 if( nodeName === "do" || (nodeName === "stop" && parent === env.i[name].__run ) ) return;
69 if(_.isFunction(target)) {
70 var Node;
71 if(setup) Node = setup(nodeName, cached? env.getCached(target) : target, path );
72 else if (cached) Node = env.getCached(target);
73 else Node = target;
74
75 if(Node){
76 parent[nodeName] = Node;
77 if(Node.setupNode) initializers.push(Node.setupNode);
78 }
79 else delete parent[nodeName];
80 }
81 else target.do = actual_do;
82 });
83 env.i[name].__run = { stop: env.stop };
84
85 if(initializers.length) env.helpers.chain(initializers)(cb, env);
86 else cb();
87 }
88
89 }
90
91 env.engines = {};
92 env.i = {};
93 env.classes = {};
94
95
96 function findCbAndRespond(args, msg){
97 var cb = _.last(args);
98 if(_.isFunction(cb)) cb(msg)
99 }
100
101
102 var DO = function(address){
103 var args = Array.prototype.slice.call(arguments);
104 var address = args[0];
105 var address_parts = address.split(".");
106 var root = env.i[address_parts[0]];
107 if(!root) return findCbAndRespond(args, "Can't find target: ", address);
108 var last = _.last(address_parts);
109 var context = env.helpers.resolve(env.i, address_parts.slice(0, -1).join("."));
110 if(!context || !(_.isFunction(context[last]))) return findCbAndRespond(args, "Can't find target: "+address);
111
112 if(context.parseArguments) args = context.parseArguments(args.slice(1));
113 else args = args.slice(1);
114 context[last].apply(context, args);
115 };
116
117
118 if(config.process_mode === "cluster"){
119
120 var callbacks = {}, cb_index = 0;
121 env.serializeCallback = function serializeCallback(fn){
122 cb_index++;
123 callbacks[cb_index] = fn;
124 return cb_index;
125 }
126
127 env.runCallback = function runCallback(data){
128 var fn = callbacks[data.run_cb[1]];
129 if(fn) {
130 fn.apply(global, data.args);
131 if(!fn.isListener && !fn.isStream){
132 env.dropCallback({drop_cb: data.run_cb});
133 }
134 }
135 }
136
137 env.dropCallback = function runCallback(data){
138 var fn = callbacks[data.drop_cb[1]];
139 if(fn) {
140 delete callbacks[data.drop_cb[1]];
141 }
142 }
143
144 var cluster = require("cluster");
145 if(cluster.isMaster){
146 require("./init/process/master.js")(env, cb);
147 }
148 else{
149
150 env.deserializeCallback = function deserializeCallback(cb_data){
151 var cb = Array.prototype.slice.call(cb_data);
152 return function(){
153 process.send({
154 address: cb[0],
155 run_cb: cb,
156 args: Array.prototype.slice.call(arguments)
157 });
158 }
159 }
160
161 env.deserializeStream = function deserializeStream(stream_data){
162 var stream = Array.prototype.slice.call(stream_data);
163 var deserialized = function(){
164 process.send({
165 address: stream[0],
166 run_cb: stream,
167 args: Array.prototype.slice.call(arguments)
168 });
169 }
170 deserialized.end = function(){ process.send({ address: stream[0], drop_cb: stream }); }
171 return deserialized;
172 }
173
174 env.deserializeListener = function deserializeListener(listener_data){
175 var listener = Array.prototype.slice.call(listener_data);
176 var deserialized = function(){
177 process.send({
178 address: listener[0],
179 run_cb: listener,
180 args: Array.prototype.slice.call(arguments)
181 });
182 }
183 deserialized.drop = function(){ process.send({ address: listener[0], drop_cb: listener }); };
184 return deserialized;
185 }
186
187 actual_do = env.i.do;
188
189 require("./init/process/worker.js")(env, cb);
190 }
191 }
192 else {
193 // Flatten partial configurations in structures
194 if(config.structures){
195 _.each(config.structures, function(structure){
196 if(structure.config){
197 var partial_config = structure.config;
198 _.extend(config, partial_config);
199 delete structure.config;
200 }
201 });
202 }
203
204 actual_do = DO;
205
206
207 var calls_cache = [];
208 env.i.do = function(){
209 calls_cache.push(arguments);
210 }
211 require("./init/process/single.js")(env, function(err){
212 if(err) return cb(err);
213
214 env.i.do = DO;
215
216 for(var i=0;i<calls_cache.length; i++){
217 DO.apply(env.i, calls_cache[i]);
218 }
219 delete calls_cache;
220
221 cb(null, env);
222 });
223 }
224
225 // if (!env.config.nodes && cluster.isMaster) require("./init/single.js")(env, cb);
226 // else if (env.config.nodes && cluster.isMaster) require("./init/master.js")(env, cb);
227 // else require("./init/worker.js")(env, cb);
228
229
230};