Builder/Provider/Project/Base.js
[app.Builder.js] / Builder / Provider / Project / Base.js
1 //<Script type="text/javascript">
2
3 /**
4  * Project Object
5  * 
6  * Projects can only contain one directory... - it can import other projects..(later)
7  * 
8  * we need to sort out that - paths is currently a key/value array..
9  * 
10  * 
11  * 
12  */
13
14 Gio = imports.gi.Gio;
15 GLib = imports.gi.GLib; 
16
17
18 console = imports.console;
19 XObject = imports.XObject.XObject;
20
21 ProjectManager = imports.Builder.Provider.ProjectManager.ProjectManager;
22 Observable = imports.Observable.Observable;
23
24 Base = XObject.define( 
25     function(cfg) {
26         
27         
28         this.addEvents({ 'changed'  : true });
29         var _this = this;
30         this.on('changed' , function() {
31             Seed.print("Calling PM - changed");
32             
33             ProjectManager.fireEvent('changed');
34         });
35         XObject.extend(this, cfg);
36         this.files = { }; 
37         /*
38         if (this.files ){
39             for (var f in this.files) {
40                 var xt = this.xtype;
41                 var cls = imports.Builder.Provider.File[xt][xt];
42                 this.files[f] = cls(this.files[f]);
43             }
44         }
45         */
46         
47         
48         this.scanDirs();
49         
50     },
51     Observable, 
52     {
53         id : false,
54         fn:  false, // the md5 sum for this one..
55         paths : false,
56         files : false,
57         tree : false,
58         xtype : false,
59         
60         load : function (o)  // is this used??
61         {
62             if (!this.fetchTree) {
63                 console.log("Project.getTree tree called on base object?!?!");
64                 return false;
65             }
66             
67             if (this.files) {
68                 return o.success.apply(o.scope || this, [this]);
69             }
70             return this.fetchTree(o);
71             
72         },
73         getPalete : function()
74         {
75             print("GET PROVIDER FOR " + this.xtype);
76             return  ProjectManager.getPalete(this.xtype);
77         },
78         toJSON : function()
79         {
80             var ret = { };
81             var _this = this;
82             for (var k in _this) {
83                 
84                 if (['files', 'tree'].indexOf(k) > -1) {
85                     continue;
86                 }
87                 if ((typeof(_this[k]) == 'object') ||(typeof(_this[k]) == 'function')) {
88                     continue;
89                 }
90                 print("Storing " + k);
91                 ret[k] = _this[k];
92                 
93             }
94             
95             
96             // deal with files..
97             //for (var f in this.files) {
98             //    print(f);
99             //    ret.files[f] = this.files[f].toJsonArray();
100            // }
101             
102             
103             return JSON.stringify(ret);
104           
105           
106         },
107         toTree : function()
108         {
109             
110             
111             // normally this will build tree's based on info in the file stuff..
112             // but for the time being, we just return an array of all the files.
113             
114             
115             
116             //if (this.tree) {
117              //   return this.tree;
118             //}
119             
120             this.tree = [];
121             /*
122             for (var f in this.files) {
123                 this.tree.push(this.files[f]);
124             }
125             return this.tree;
126             */
127             
128             // have parents -> add them to parent...
129             var files = {};
130             var parents = {};
131             for (var k in this.files) {
132                 
133                 var f = this.files[k];
134                 if (!f) {
135                     continue;
136                    }
137                 ///console.dump(f);
138                 f.hasParent = false;
139                 f.cn = [];
140                 //console.log(f.name);
141                 if (f.fullname) {
142                     files[f.fullname] = f;
143                 }
144             };
145             
146             // add Parent pointer..
147             for (var k in this.files) {
148                 var f = this.files[k];
149                 console.log(f.parent + ":" + f.name);
150                 if (f.parent && typeof(files[f.parent]) != 'undefined') {
151                     // add it to parent;
152                     
153                     files[f.parent].cn.push(f);
154                     f.hasParent = true;
155                     
156                 }
157                 
158                 
159             };
160             
161               
162             
163             var ret = [];
164             for (var k in this.files) {
165                 var f = this.files[k];
166                 
167                 f.sortCn();
168                 if (f.hasParent) {
169                     continue;
170                 }
171                 if (typeof(files[f.fullname]) != 'undefined') {
172                     ret.push(f);
173                 }
174                 
175             };
176             
177             
178             ret.sort(function(a,b) {
179                 return a.path > b.path ? 1 : -1;
180             });
181             this.tree = ret;
182             return this.tree;
183              
184             
185         },
186         getById : function(id)
187         {
188             var ret = false;
189             for (var k in this.files) {
190                 var f = this.files[k];
191                 
192                 console.log(f.id + '?=' + id);
193                 if (f.id == id) {
194                     return f;
195                 }
196             };
197             return ret;
198         },
199         
200         loadFileOnly : function(path)
201         {
202             
203             var xt = this.xtype;
204             var cls = imports.Builder.Provider.File[xt][xt];
205             return  new cls({
206                 path : path,
207                 parent : '',
208                 project : this
209             });
210         },
211         create : function(filename)
212         {
213             var ret = this.loadFileOnly(filename);
214             ret.save();
215             this.addFile(ret);
216             return ret;
217             
218         },
219         
220          
221         addFile: function(pfile) { // add a single file, and trigger changed.
222             this.files[pfile.path] = pfile
223             this.fireEvent('changed', this);
224         },
225         
226         add: function(path, type)
227         {
228             this.paths = this.paths || { };
229             this.paths[path] = type;
230             //Seed.print(" type is '" + type + "'");
231             if (type == 'dir') {
232                 this.scanDir(path);
233             //    console.dump(this.files);
234             }
235             if (type == 'file' ) {
236                 
237                 this.files[path] = this.loadFileOnly( path );
238             }
239             
240             // console.dump(this.files);
241             this.fireEvent('changed', this);
242             
243         },
244         
245         scanDirs: function()
246         {
247             this.files = this.files  || { };
248             for (var d in this.paths) {
249                 if (this.paths[d] == 'dir') {
250                     this.scanDir(d);
251                 }
252                 // otherwise add a file..
253             }
254             //console.dump(this.files);
255             
256         },
257         
258         
259         // list files.
260         scanDir : function(dir, dp) 
261         {
262             dp = dp || 0;
263             Seed.print("Running scandir on " + dir);
264             if (dp > 5) { // no more than 5 deep?
265                 return;
266             }
267             // this should be done async -- but since we are getting the proto up ...
268             var gdir = GLib.dir_open(dir,0);
269             var subs = [];
270             var _this = this;
271             while (true) {
272                 var fn = GLib.dir_read_name(gdir);
273                 console.log('trying ' + dir + '/' + fn);
274                 if (!fn) {
275                     GLib.dir_close(gdir);
276                     subs.forEach( function(s) {
277                         _this.scanDir(s, dp+1);
278                     });
279                     return;
280                 }
281                 if (fn[0] == '.') { // skip hidden
282                     continue;
283                 }
284                 
285                 if (GLib.file_test(dir  + '/' + fn, GLib.FileTest.IS_DIR)) {
286                     subs.push(dir  + '/' + fn);
287                     continue;
288                 }
289                 
290                 if (!fn.match(/\.bjs$/)) {
291                     continue;
292                 }
293                 var parent = '';
294                 //if (dp > 0 ) {
295                 var sp = dir.split('/');
296                 sp = sp.splice(sp.length - (dp +1), (dp +1));
297                 parent = sp.join('.');
298                 
299                 
300                 if (typeof(this.files[dir  + '/' + fn]) != 'undefined') {
301                     // we already have it..
302                     this.files[dir  + '/' + fn].parent = parent;
303                     continue;
304                 }
305                 var xt = this.xtype;
306                 var cls = imports.Builder.Provider.File[xt][xt];
307                 
308                 Seed.print("Adding file " + dir  + '/' + fn);
309                 this.files[dir  + '/' + fn] = new cls({
310                     path : dir  + '/' + fn,
311                     parent : parent,
312                     project : this
313                 });
314                 //console.log(this.files[dir  + '/' + fn] );
315                 /*
316                 var f = Gio.file_new_for_path(dir + '/' + fn);
317                 var inf = f.query_info('standard::*');
318                 var tv = new GLib.TimeVal();
319                 inf.get_modification_time(tv);
320                 
321                 // should it do something about this information..
322                 // fixme... time data is busted..
323                 this.files[dir  + '/' + fn] = '' + tv.tv_sec + '.' + tv.tv_usec;
324                 */
325             }
326              
327             
328         }
329         
330         
331         
332         
333         
334
335     }
336 ); 
337
338
339      
340