OLD | NEW |
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 /* This file defines the module loader for the dart runtime. | 5 /* This file defines the module loader for the dart runtime. |
6 */ | 6 */ |
7 | 7 |
8 var dart_library = | 8 var dart_library = |
9 typeof module != "undefined" && module.exports || {}; | 9 typeof module != "undefined" && module.exports || {}; |
10 | 10 |
11 (function (dart_library) { | 11 (function (dart_library) { |
12 'use strict'; | 12 'use strict'; |
13 | 13 |
14 /** Note that we cannot use dart_utils.throwInternalError from here. */ | 14 /** Note that we cannot use dart_utils.throwInternalError from here. */ |
15 function throwLibraryError(message) { | 15 function throwLibraryError(message) { |
16 throw Error(message); | 16 throw Error(message); |
17 } | 17 } |
18 | 18 |
19 // Module support. This is a simplified module system for Dart. | 19 // Module support. This is a simplified module system for Dart. |
20 // Longer term, we can easily migrate to an existing JS module system: | 20 // Longer term, we can easily migrate to an existing JS module system: |
21 // ES6, AMD, RequireJS, .... | 21 // ES6, AMD, RequireJS, .... |
22 | 22 |
23 class LibraryLoader { | 23 class LibraryLoader { |
24 constructor(name, defaultValue, imports, lazyImports, loader) { | 24 constructor(name, defaultValue, imports, loader) { |
25 this._name = name; | 25 this._name = name; |
26 this._library = defaultValue ? defaultValue : {}; | 26 this._library = defaultValue ? defaultValue : {}; |
27 this._imports = imports; | 27 this._imports = imports; |
28 this._lazyImports = lazyImports; | |
29 this._loader = loader; | 28 this._loader = loader; |
30 | 29 |
31 // Cyclic import detection | 30 // Cyclic import detection |
32 this._state = LibraryLoader.NOT_LOADED; | 31 this._state = LibraryLoader.NOT_LOADED; |
33 } | 32 } |
34 | 33 |
35 loadImports(pendingSet) { | 34 loadImports() { |
36 return this.handleImports(this._imports, (lib) => lib.load(pendingSet)); | |
37 } | |
38 | |
39 deferLazyImports(pendingSet) { | |
40 return this.handleImports(this._lazyImports, | |
41 (lib) => { | |
42 pendingSet.add(lib._name); | |
43 return lib.stub(); | |
44 }); | |
45 } | |
46 | |
47 loadLazyImports(pendingSet) { | |
48 return this.handleImports(pendingSet, (lib) => lib.load()); | |
49 } | |
50 | |
51 handleImports(list, handler) { | |
52 let results = []; | 35 let results = []; |
53 for (let name of list) { | 36 for (let name of this._imports) { |
54 let lib = libraries.get(name); | 37 let lib = libraries.get(name); |
55 if (!lib) { | 38 if (!lib) { |
56 throwLibraryError('Library not available: ' + name); | 39 throwLibraryError('Library not available: ' + name); |
57 } | 40 } |
58 results.push(handler(lib)); | 41 results.push(lib.load()); |
59 } | 42 } |
60 return results; | 43 return results; |
61 } | 44 } |
62 | 45 |
63 load(inheritedPendingSet) { | 46 load() { |
64 // Check for cycles | 47 // Check for cycles |
65 if (this._state == LibraryLoader.LOADING) { | 48 if (this._state == LibraryLoader.LOADING) { |
66 throwLibraryError('Circular dependence on library: ' | 49 throwLibraryError('Circular dependence on library: ' |
67 + this._name); | 50 + this._name); |
68 } else if (this._state >= LibraryLoader.LOADED) { | 51 } else if (this._state >= LibraryLoader.READY) { |
69 return this._library; | 52 return this._library; |
70 } | 53 } |
71 this._state = LibraryLoader.LOADING; | 54 this._state = LibraryLoader.LOADING; |
72 | 55 |
73 // Handle imports and record lazy imports | 56 // Handle imports |
74 let pendingSet = inheritedPendingSet ? inheritedPendingSet : new Set(); | 57 let args = this.loadImports(); |
75 let args = this.loadImports(pendingSet); | |
76 args = args.concat(this.deferLazyImports(pendingSet)); | |
77 | 58 |
78 // Load the library | 59 // Load the library |
79 args.unshift(this._library); | 60 args.unshift(this._library); |
80 this._loader.apply(null, args); | 61 this._loader.apply(null, args); |
81 this._state = LibraryLoader.LOADED; | |
82 | |
83 // Handle lazy imports | |
84 if (inheritedPendingSet === void 0) { | |
85 // Drain the queue | |
86 this.loadLazyImports(pendingSet); | |
87 } | |
88 this._state = LibraryLoader.READY; | 62 this._state = LibraryLoader.READY; |
89 return this._library; | 63 return this._library; |
90 } | 64 } |
91 | 65 |
92 stub() { | 66 stub() { |
93 return this._library; | 67 return this._library; |
94 } | 68 } |
95 } | 69 } |
96 LibraryLoader.NOT_LOADED = 0; | 70 LibraryLoader.NOT_LOADED = 0; |
97 LibraryLoader.LOADING = 1; | 71 LibraryLoader.LOADING = 1; |
98 LibraryLoader.LOADED = 2; | 72 LibraryLoader.READY = 2; |
99 LibraryLoader.READY = 3; | |
100 | 73 |
101 // Map from name to LibraryLoader | 74 // Map from name to LibraryLoader |
102 let libraries = new Map(); | 75 let libraries = new Map(); |
103 dart_library.libraries = function() { return libraries.keys(); } | 76 dart_library.libraries = function() { return libraries.keys(); }; |
104 | 77 |
105 function library(name, defaultValue, imports, lazyImports, loader) { | 78 function library(name, defaultValue, imports, loader) { |
106 let result = new LibraryLoader(name, defaultValue, imports, lazyImports, loa
der); | 79 let result = new LibraryLoader(name, defaultValue, imports, loader); |
107 libraries.set(name, result); | 80 libraries.set(name, result); |
108 return result; | 81 return result; |
109 } | 82 } |
110 dart_library.library = library; | 83 dart_library.library = library; |
111 | 84 |
112 function import_(libraryName) { | 85 function import_(libraryName) { |
113 bootstrap(); | 86 bootstrap(); |
114 let loader = libraries.get(libraryName); | 87 let loader = libraries.get(libraryName); |
115 // TODO(vsm): A user might call this directly from JS (as we do in tests). | 88 // TODO(vsm): A user might call this directly from JS (as we do in tests). |
116 // We may want a different error type. | 89 // We may want a different error type. |
117 if (!loader) throwLibraryError('Library not found: ' + libraryName); | 90 if (!loader) throwLibraryError('Library not found: ' + libraryName); |
118 return loader.load(); | 91 return loader.load(); |
119 } | 92 } |
120 dart_library.import = import_; | 93 dart_library.import = import_; |
121 | 94 |
122 function start(libraryName) { | 95 function start(moduleName, libraryName) { |
123 let library = import_(libraryName); | 96 if (libraryName == null) libraryName = moduleName; |
124 let _isolate_helper = import_('dart/_isolate_helper'); | 97 let library = import_(moduleName)[libraryName]; |
125 _isolate_helper.startRootIsolate(library.main, []); | 98 let dart_sdk = import_('dart_sdk'); |
| 99 dart_sdk._isolate_helper.startRootIsolate(library.main, []); |
126 } | 100 } |
127 dart_library.start = start; | 101 dart_library.start = start; |
128 | 102 |
129 let _bootstrapped = false; | 103 let _bootstrapped = false; |
130 function bootstrap() { | 104 function bootstrap() { |
131 if (_bootstrapped) return; | 105 if (_bootstrapped) return; |
132 _bootstrapped = true; | 106 _bootstrapped = true; |
133 | 107 |
134 // Force import of core. | 108 // Force import of core. |
135 var core = import_('dart/core'); | 109 var dart_sdk = import_('dart_sdk'); |
| 110 var core = dart_sdk.core; |
| 111 |
| 112 // TODO(jmesserly): this can't be right. |
| 113 // See: https://github.com/dart-lang/dev_compiler/issues/488 |
136 core.Object.toString = function() { | 114 core.Object.toString = function() { |
137 // Interface types are represented by the corresponding constructor | 115 // Interface types are represented by the corresponding constructor |
138 // function. This ensures that Dart interface types print properly. | 116 // function. This ensures that Dart interface types print properly. |
139 return this.name; | 117 return this.name; |
140 } | 118 } |
141 | 119 |
142 // TODO(vsm): DOM facades? | 120 // TODO(vsm): DOM facades? |
143 // See: https://github.com/dart-lang/dev_compiler/issues/173 | 121 // See: https://github.com/dart-lang/dev_compiler/issues/173 |
144 if (typeof NodeList !== "undefined") { | 122 if (typeof NodeList !== "undefined") { |
145 NodeList.prototype.get = function(i) { return this[i]; }; | 123 NodeList.prototype.get = function(i) { return this[i]; }; |
146 NamedNodeMap.prototype.get = function(i) { return this[i]; }; | 124 NamedNodeMap.prototype.get = function(i) { return this[i]; }; |
147 DOMTokenList.prototype.get = function(i) { return this[i]; }; | 125 DOMTokenList.prototype.get = function(i) { return this[i]; }; |
148 HTMLCollection.prototype.get = function(i) { return this[i]; }; | 126 HTMLCollection.prototype.get = function(i) { return this[i]; }; |
149 } | 127 } |
150 | 128 |
151 // This import is only needed for chrome debugging. We should provide an | 129 // This import is only needed for chrome debugging. We should provide an |
152 // option to compile without it. | 130 // option to compile without it. |
153 var devtoolsDebugger = import_('dart/_debugger'); | 131 dart_sdk._debugger.registerDevtoolsFormatter(); |
154 devtoolsDebugger.registerDevtoolsFormatter(); | |
155 } | 132 } |
156 | 133 |
157 })(dart_library); | 134 })(dart_library); |
OLD | NEW |