brighterscript 1.0.0-alpha.40 → 1.0.0-alpha.42
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +67 -1
- package/dist/AstValidationSegmenter.d.ts +3 -0
- package/dist/AstValidationSegmenter.js +62 -2
- package/dist/AstValidationSegmenter.js.map +1 -1
- package/dist/BsConfig.d.ts +7 -7
- package/dist/CrossScopeValidator.js +3 -3
- package/dist/CrossScopeValidator.js.map +1 -1
- package/dist/DiagnosticFilterer.d.ts +5 -1
- package/dist/DiagnosticFilterer.js +92 -33
- package/dist/DiagnosticFilterer.js.map +1 -1
- package/dist/DiagnosticManager.js +12 -9
- package/dist/DiagnosticManager.js.map +1 -1
- package/dist/DiagnosticMessages.d.ts +374 -225
- package/dist/DiagnosticMessages.js +641 -424
- package/dist/DiagnosticMessages.js.map +1 -1
- package/dist/DiagnosticSeverityAdjuster.js +4 -0
- package/dist/DiagnosticSeverityAdjuster.js.map +1 -1
- package/dist/LanguageServer.js +0 -7
- package/dist/LanguageServer.js.map +1 -1
- package/dist/PluginInterface.js +2 -0
- package/dist/PluginInterface.js.map +1 -1
- package/dist/Program.d.ts +22 -1
- package/dist/Program.js +206 -49
- package/dist/Program.js.map +1 -1
- package/dist/SymbolTable.d.ts +3 -0
- package/dist/SymbolTable.js +19 -1
- package/dist/SymbolTable.js.map +1 -1
- package/dist/XmlScope.js +3 -6
- package/dist/XmlScope.js.map +1 -1
- package/dist/astUtils/creators.d.ts +35 -3
- package/dist/astUtils/creators.js +52 -1
- package/dist/astUtils/creators.js.map +1 -1
- package/dist/astUtils/reflection.d.ts +4 -2
- package/dist/astUtils/reflection.js +12 -3
- package/dist/astUtils/reflection.js.map +1 -1
- package/dist/astUtils/visitors.d.ts +3 -2
- package/dist/astUtils/visitors.js +37 -14
- package/dist/astUtils/visitors.js.map +1 -1
- package/dist/astUtils/visitors.spec.js +172 -6
- package/dist/astUtils/visitors.spec.js.map +1 -1
- package/dist/bscPlugin/codeActions/CodeActionsProcessor.d.ts +0 -1
- package/dist/bscPlugin/codeActions/CodeActionsProcessor.js +0 -13
- package/dist/bscPlugin/codeActions/CodeActionsProcessor.js.map +1 -1
- package/dist/bscPlugin/completions/CompletionsProcessor.d.ts +2 -1
- package/dist/bscPlugin/completions/CompletionsProcessor.js +5 -5
- package/dist/bscPlugin/completions/CompletionsProcessor.js.map +1 -1
- package/dist/bscPlugin/completions/CompletionsProcessor.spec.js +106 -2
- package/dist/bscPlugin/completions/CompletionsProcessor.spec.js.map +1 -1
- package/dist/bscPlugin/hover/HoverProcessor.spec.js +51 -3
- package/dist/bscPlugin/hover/HoverProcessor.spec.js.map +1 -1
- package/dist/bscPlugin/transpile/BrsFileTranspileProcessor.d.ts +1 -0
- package/dist/bscPlugin/transpile/BrsFileTranspileProcessor.js +149 -0
- package/dist/bscPlugin/transpile/BrsFileTranspileProcessor.js.map +1 -1
- package/dist/bscPlugin/validation/BrsFileValidator.js +15 -8
- package/dist/bscPlugin/validation/BrsFileValidator.js.map +1 -1
- package/dist/bscPlugin/validation/BrsFileValidator.spec.js +80 -9
- package/dist/bscPlugin/validation/BrsFileValidator.spec.js.map +1 -1
- package/dist/bscPlugin/validation/ScopeValidator.d.ts +9 -0
- package/dist/bscPlugin/validation/ScopeValidator.js +155 -79
- package/dist/bscPlugin/validation/ScopeValidator.js.map +1 -1
- package/dist/bscPlugin/validation/ScopeValidator.spec.js +1269 -35
- package/dist/bscPlugin/validation/ScopeValidator.spec.js.map +1 -1
- package/dist/bscPlugin/validation/XmlFileValidator.js +0 -8
- package/dist/bscPlugin/validation/XmlFileValidator.js.map +1 -1
- package/dist/diagnosticUtils.js +6 -5
- package/dist/diagnosticUtils.js.map +1 -1
- package/dist/files/BrsFile.Class.spec.js +87 -28
- package/dist/files/BrsFile.Class.spec.js.map +1 -1
- package/dist/files/BrsFile.d.ts +1 -0
- package/dist/files/BrsFile.js +20 -8
- package/dist/files/BrsFile.js.map +1 -1
- package/dist/files/BrsFile.spec.js +133 -34
- package/dist/files/BrsFile.spec.js.map +1 -1
- package/dist/files/XmlFile.js +2 -2
- package/dist/files/XmlFile.js.map +1 -1
- package/dist/files/XmlFile.spec.js +3 -20
- package/dist/files/XmlFile.spec.js.map +1 -1
- package/dist/globalCallables.js +1 -1
- package/dist/index.d.ts +8 -3
- package/dist/index.js +24 -16
- package/dist/index.js.map +1 -1
- package/dist/interfaces.d.ts +18 -0
- package/dist/interfaces.js.map +1 -1
- package/dist/lexer/Lexer.js +17 -11
- package/dist/lexer/Lexer.js.map +1 -1
- package/dist/lexer/Lexer.spec.js +21 -3
- package/dist/lexer/Lexer.spec.js.map +1 -1
- package/dist/lexer/TokenKind.d.ts +9 -0
- package/dist/lexer/TokenKind.js +11 -1
- package/dist/lexer/TokenKind.js.map +1 -1
- package/dist/parser/AstNode.d.ts +2 -1
- package/dist/parser/AstNode.js +3 -2
- package/dist/parser/AstNode.js.map +1 -1
- package/dist/parser/Expression.d.ts +22 -2
- package/dist/parser/Expression.js +76 -48
- package/dist/parser/Expression.js.map +1 -1
- package/dist/parser/Parser.Class.spec.js +3 -3
- package/dist/parser/Parser.Class.spec.js.map +1 -1
- package/dist/parser/Parser.js +73 -61
- package/dist/parser/Parser.js.map +1 -1
- package/dist/parser/Parser.spec.js +198 -15
- package/dist/parser/Parser.spec.js.map +1 -1
- package/dist/parser/SGParser.js +9 -9
- package/dist/parser/SGParser.js.map +1 -1
- package/dist/parser/SGParser.spec.js +3 -2
- package/dist/parser/SGParser.spec.js.map +1 -1
- package/dist/parser/Statement.d.ts +16 -18
- package/dist/parser/Statement.js +136 -82
- package/dist/parser/Statement.js.map +1 -1
- package/dist/parser/tests/controlFlow/If.spec.js +1 -1
- package/dist/parser/tests/controlFlow/If.spec.js.map +1 -1
- package/dist/parser/tests/expression/ArrayLiterals.spec.js +3 -3
- package/dist/parser/tests/expression/ArrayLiterals.spec.js.map +1 -1
- package/dist/parser/tests/expression/AssociativeArrayLiterals.spec.js +3 -3
- package/dist/parser/tests/expression/AssociativeArrayLiterals.spec.js.map +1 -1
- package/dist/parser/tests/expression/Call.spec.js +9 -9
- package/dist/parser/tests/expression/Call.spec.js.map +1 -1
- package/dist/parser/tests/expression/Indexing.spec.js +3 -3
- package/dist/parser/tests/expression/Indexing.spec.js.map +1 -1
- package/dist/parser/tests/expression/TemplateStringExpression.spec.js +1 -1
- package/dist/parser/tests/expression/TemplateStringExpression.spec.js.map +1 -1
- package/dist/parser/tests/expression/TernaryExpression.spec.js +353 -71
- package/dist/parser/tests/expression/TernaryExpression.spec.js.map +1 -1
- package/dist/parser/tests/statement/Dim.spec.js +10 -3
- package/dist/parser/tests/statement/Dim.spec.js.map +1 -1
- package/dist/parser/tests/statement/Enum.spec.js +2 -2
- package/dist/parser/tests/statement/Enum.spec.js.map +1 -1
- package/dist/parser/tests/statement/Increment.spec.js +3 -5
- package/dist/parser/tests/statement/Increment.spec.js.map +1 -1
- package/dist/parser/tests/statement/PrintStatement.spec.js +3 -3
- package/dist/parser/tests/statement/TryCatch.spec.js +1 -1
- package/dist/parser/tests/statement/TryCatch.spec.js.map +1 -1
- package/dist/roku-types/data.json +430 -235
- package/dist/roku-types/index.d.ts +30 -37
- package/dist/types/ArrayType.d.ts +2 -0
- package/dist/types/ArrayType.js +14 -4
- package/dist/types/ArrayType.js.map +1 -1
- package/dist/types/AssociativeArrayType.d.ts +1 -0
- package/dist/types/AssociativeArrayType.js +1 -0
- package/dist/types/AssociativeArrayType.js.map +1 -1
- package/dist/types/BaseFunctionType.d.ts +1 -0
- package/dist/types/BaseFunctionType.js +1 -0
- package/dist/types/BaseFunctionType.js.map +1 -1
- package/dist/types/BooleanType.d.ts +1 -0
- package/dist/types/BooleanType.js +1 -0
- package/dist/types/BooleanType.js.map +1 -1
- package/dist/types/BscType.d.ts +8 -1
- package/dist/types/BscType.js +12 -3
- package/dist/types/BscType.js.map +1 -1
- package/dist/types/BuiltInInterfaceAdder.js +10 -6
- package/dist/types/BuiltInInterfaceAdder.js.map +1 -1
- package/dist/types/ClassType.d.ts +1 -0
- package/dist/types/ClassType.js +5 -2
- package/dist/types/ClassType.js.map +1 -1
- package/dist/types/ComponentType.d.ts +11 -4
- package/dist/types/ComponentType.js +100 -8
- package/dist/types/ComponentType.js.map +1 -1
- package/dist/types/DoubleType.d.ts +2 -0
- package/dist/types/DoubleType.js +2 -0
- package/dist/types/DoubleType.js.map +1 -1
- package/dist/types/DynamicType.d.ts +1 -0
- package/dist/types/DynamicType.js +4 -0
- package/dist/types/DynamicType.js.map +1 -1
- package/dist/types/EnumType.d.ts +2 -0
- package/dist/types/EnumType.js +20 -2
- package/dist/types/EnumType.js.map +1 -1
- package/dist/types/FloatType.d.ts +2 -0
- package/dist/types/FloatType.js +2 -0
- package/dist/types/FloatType.js.map +1 -1
- package/dist/types/InheritableType.d.ts +1 -0
- package/dist/types/InheritableType.js +14 -1
- package/dist/types/InheritableType.js.map +1 -1
- package/dist/types/IntegerType.d.ts +2 -0
- package/dist/types/IntegerType.js +2 -0
- package/dist/types/IntegerType.js.map +1 -1
- package/dist/types/InterfaceType.js +4 -1
- package/dist/types/InterfaceType.js.map +1 -1
- package/dist/types/InvalidType.d.ts +2 -1
- package/dist/types/InvalidType.js +1 -0
- package/dist/types/InvalidType.js.map +1 -1
- package/dist/types/LongIntegerType.d.ts +2 -0
- package/dist/types/LongIntegerType.js +2 -0
- package/dist/types/LongIntegerType.js.map +1 -1
- package/dist/types/ObjectType.d.ts +1 -0
- package/dist/types/ObjectType.js +1 -0
- package/dist/types/ObjectType.js.map +1 -1
- package/dist/types/ReferenceType.d.ts +20 -2
- package/dist/types/ReferenceType.js +106 -5
- package/dist/types/ReferenceType.js.map +1 -1
- package/dist/types/StringType.d.ts +1 -0
- package/dist/types/StringType.js +1 -0
- package/dist/types/StringType.js.map +1 -1
- package/dist/types/TypedFunctionType.d.ts +1 -1
- package/dist/types/TypedFunctionType.js +8 -2
- package/dist/types/TypedFunctionType.js.map +1 -1
- package/dist/types/UninitializedType.d.ts +2 -0
- package/dist/types/UninitializedType.js +5 -6
- package/dist/types/UninitializedType.js.map +1 -1
- package/dist/types/UnionType.js +8 -2
- package/dist/types/UnionType.js.map +1 -1
- package/dist/types/VoidType.d.ts +4 -1
- package/dist/types/VoidType.js +5 -0
- package/dist/types/VoidType.js.map +1 -1
- package/dist/types/helpers.js +8 -1
- package/dist/types/helpers.js.map +1 -1
- package/dist/util.d.ts +15 -5
- package/dist/util.js +281 -14
- package/dist/util.js.map +1 -1
- package/dist/validators/ClassValidator.js +13 -5
- package/dist/validators/ClassValidator.js.map +1 -1
- package/package.json +2 -2
package/dist/Program.js
CHANGED
|
@@ -44,6 +44,8 @@ const thenby_1 = require("thenby");
|
|
|
44
44
|
const CrossScopeValidator_1 = require("./CrossScopeValidator");
|
|
45
45
|
const DiagnosticManager_1 = require("./DiagnosticManager");
|
|
46
46
|
const ProgramValidator_1 = require("./bscPlugin/validation/ProgramValidator");
|
|
47
|
+
const SymbolTable_1 = require("./SymbolTable");
|
|
48
|
+
const types_1 = require("./types");
|
|
47
49
|
const bslibNonAliasedRokuModulesPkgPath = (0, util_1.standardizePath) `source/roku_modules/rokucommunity_bslib/bslib.brs`;
|
|
48
50
|
const bslibAliasedRokuModulesPkgPath = (0, util_1.standardizePath) `source/roku_modules/bslib/bslib.brs`;
|
|
49
51
|
class Program {
|
|
@@ -69,6 +71,17 @@ class Program {
|
|
|
69
71
|
*/
|
|
70
72
|
this.globalScope = undefined;
|
|
71
73
|
this.fileSymbolInformation = new Map();
|
|
74
|
+
/**
|
|
75
|
+
* Map of typetime symbols which depend upon the key symbol
|
|
76
|
+
*/
|
|
77
|
+
this.symbolDependencies = new Map();
|
|
78
|
+
/**
|
|
79
|
+
* Symbol Table for storing custom component types
|
|
80
|
+
* This is a sibling to the global table (as Components can be used/referenced anywhere)
|
|
81
|
+
* Keeping custom components out of the global table and in a specific symbol table
|
|
82
|
+
* compartmentalizes their use
|
|
83
|
+
*/
|
|
84
|
+
this.componentsTable = new SymbolTable_1.SymbolTable('Custom Components');
|
|
72
85
|
/**
|
|
73
86
|
* A map of every file loaded into this program, indexed by its original file location
|
|
74
87
|
*/
|
|
@@ -93,8 +106,9 @@ class Program {
|
|
|
93
106
|
this.components = {};
|
|
94
107
|
/**
|
|
95
108
|
* Keeps a set of all the components that need to have their types updated during the current validation cycle
|
|
109
|
+
* Map <componentKey, componentName>
|
|
96
110
|
*/
|
|
97
|
-
this.componentSymbolsToUpdate = new
|
|
111
|
+
this.componentSymbolsToUpdate = new Map();
|
|
98
112
|
this.crossScopeValidation = new CrossScopeValidator_1.CrossScopeValidator(this);
|
|
99
113
|
this.isFirstValidation = true;
|
|
100
114
|
this.sortedScopeNames = undefined;
|
|
@@ -121,6 +135,7 @@ class Program {
|
|
|
121
135
|
this.globalScope.attachDependencyGraph(this.dependencyGraph);
|
|
122
136
|
this.scopes.global = this.globalScope;
|
|
123
137
|
this.populateGlobalSymbolTable();
|
|
138
|
+
this.globalScope.symbolTable.addSibling(this.componentsTable);
|
|
124
139
|
//hardcode the files list for global scope to only contain the global file
|
|
125
140
|
this.globalScope.getAllFiles = () => [globalCallables_1.globalFile];
|
|
126
141
|
globalCallables_1.globalFile.isValidated = true;
|
|
@@ -147,11 +162,12 @@ class Program {
|
|
|
147
162
|
}
|
|
148
163
|
nodeType = new ComponentType_1.ComponentType(nodeData.name, parentNode);
|
|
149
164
|
nodeType.addBuiltInInterfaces();
|
|
165
|
+
nodeType.isBuiltIn = true;
|
|
150
166
|
if (nodeData.name === 'Node') {
|
|
151
167
|
// Add `roSGNode` as shorthand for `roSGNodeNode`
|
|
152
|
-
this.globalScope.symbolTable.addSymbol('roSGNode', { description: nodeData.description }, nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
168
|
+
this.globalScope.symbolTable.addSymbol('roSGNode', { description: nodeData.description, isBuiltIn: true }, nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
153
169
|
}
|
|
154
|
-
this.globalScope.symbolTable.addSymbol(nodeName, { description: nodeData.description }, nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
170
|
+
this.globalScope.symbolTable.addSymbol(nodeName, { description: nodeData.description, isBuiltIn: true }, nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
155
171
|
}
|
|
156
172
|
else {
|
|
157
173
|
nodeType = this.globalScope.symbolTable.getSymbolType(nodeName, { flags: 2 /* SymbolTypeFlag.typetime */ });
|
|
@@ -163,31 +179,34 @@ class Program {
|
|
|
163
179
|
*/
|
|
164
180
|
populateGlobalSymbolTable() {
|
|
165
181
|
//Setup primitive types in global symbolTable
|
|
166
|
-
|
|
167
|
-
this.globalScope.symbolTable.addSymbol('
|
|
168
|
-
this.globalScope.symbolTable.addSymbol('
|
|
169
|
-
this.globalScope.symbolTable.addSymbol('
|
|
170
|
-
this.globalScope.symbolTable.addSymbol('
|
|
171
|
-
this.globalScope.symbolTable.addSymbol('
|
|
172
|
-
this.globalScope.symbolTable.addSymbol('
|
|
173
|
-
this.globalScope.symbolTable.addSymbol('
|
|
174
|
-
this.globalScope.symbolTable.addSymbol('
|
|
175
|
-
this.globalScope.symbolTable.addSymbol('
|
|
182
|
+
const builtInSymbolData = { isBuiltIn: true };
|
|
183
|
+
this.globalScope.symbolTable.addSymbol('boolean', builtInSymbolData, BooleanType_1.BooleanType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
184
|
+
this.globalScope.symbolTable.addSymbol('double', builtInSymbolData, DoubleType_1.DoubleType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
185
|
+
this.globalScope.symbolTable.addSymbol('dynamic', builtInSymbolData, DynamicType_1.DynamicType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
186
|
+
this.globalScope.symbolTable.addSymbol('float', builtInSymbolData, FloatType_1.FloatType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
187
|
+
this.globalScope.symbolTable.addSymbol('function', builtInSymbolData, new FunctionType_1.FunctionType(), 2 /* SymbolTypeFlag.typetime */);
|
|
188
|
+
this.globalScope.symbolTable.addSymbol('integer', builtInSymbolData, IntegerType_1.IntegerType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
189
|
+
this.globalScope.symbolTable.addSymbol('longinteger', builtInSymbolData, LongIntegerType_1.LongIntegerType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
190
|
+
this.globalScope.symbolTable.addSymbol('object', builtInSymbolData, new ObjectType_1.ObjectType(), 2 /* SymbolTypeFlag.typetime */);
|
|
191
|
+
this.globalScope.symbolTable.addSymbol('string', builtInSymbolData, StringType_1.StringType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
192
|
+
this.globalScope.symbolTable.addSymbol('void', builtInSymbolData, VoidType_1.VoidType.instance, 2 /* SymbolTypeFlag.typetime */);
|
|
176
193
|
BuiltInInterfaceAdder_1.BuiltInInterfaceAdder.getLookupTable = () => this.globalScope.symbolTable;
|
|
177
194
|
for (const callable of globalCallables_1.globalCallables) {
|
|
178
|
-
this.globalScope.symbolTable.addSymbol(callable.name, { description: callable.shortDescription }, callable.type, 1 /* SymbolTypeFlag.runtime */);
|
|
195
|
+
this.globalScope.symbolTable.addSymbol(callable.name, Object.assign(Object.assign({}, builtInSymbolData), { description: callable.shortDescription }), callable.type, 1 /* SymbolTypeFlag.runtime */);
|
|
179
196
|
}
|
|
180
197
|
for (const ifaceData of Object.values(roku_types_1.interfaces)) {
|
|
181
198
|
const nodeType = new InterfaceType_1.InterfaceType(ifaceData.name);
|
|
182
199
|
nodeType.addBuiltInInterfaces();
|
|
183
|
-
|
|
200
|
+
nodeType.isBuiltIn = true;
|
|
201
|
+
this.globalScope.symbolTable.addSymbol(ifaceData.name, Object.assign(Object.assign({}, builtInSymbolData), { description: ifaceData.description }), nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
184
202
|
}
|
|
185
203
|
for (const componentData of Object.values(roku_types_1.components)) {
|
|
186
204
|
const nodeType = new InterfaceType_1.InterfaceType(componentData.name);
|
|
187
205
|
nodeType.addBuiltInInterfaces();
|
|
206
|
+
nodeType.isBuiltIn = true;
|
|
188
207
|
if (componentData.name !== 'roSGNode') {
|
|
189
208
|
// we will add `roSGNode` as shorthand for `roSGNodeNode`, since all roSgNode components are SceneGraph nodes
|
|
190
|
-
this.globalScope.symbolTable.addSymbol(componentData.name, { description: componentData.description }, nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
209
|
+
this.globalScope.symbolTable.addSymbol(componentData.name, Object.assign(Object.assign({}, builtInSymbolData), { description: componentData.description }), nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
191
210
|
}
|
|
192
211
|
}
|
|
193
212
|
for (const nodeData of Object.values(roku_types_1.nodes)) {
|
|
@@ -196,7 +215,8 @@ class Program {
|
|
|
196
215
|
for (const eventData of Object.values(roku_types_1.events)) {
|
|
197
216
|
const nodeType = new InterfaceType_1.InterfaceType(eventData.name);
|
|
198
217
|
nodeType.addBuiltInInterfaces();
|
|
199
|
-
|
|
218
|
+
nodeType.isBuiltIn = true;
|
|
219
|
+
this.globalScope.symbolTable.addSymbol(eventData.name, Object.assign(Object.assign({}, builtInSymbolData), { description: eventData.description }), nodeType, 2 /* SymbolTypeFlag.typetime */);
|
|
200
220
|
}
|
|
201
221
|
}
|
|
202
222
|
addFileSymbolInfo(file) {
|
|
@@ -320,14 +340,19 @@ class Program {
|
|
|
320
340
|
*/
|
|
321
341
|
addDeferredComponentTypeSymbolCreation(xmlFile) {
|
|
322
342
|
var _a;
|
|
323
|
-
|
|
343
|
+
const componentKey = this.getComponentKey(xmlFile);
|
|
344
|
+
const componentName = (_a = xmlFile.componentName) === null || _a === void 0 ? void 0 : _a.text;
|
|
345
|
+
if (this.componentSymbolsToUpdate.has(componentKey)) {
|
|
346
|
+
return;
|
|
347
|
+
}
|
|
348
|
+
this.componentSymbolsToUpdate.set(componentKey, componentName);
|
|
324
349
|
}
|
|
325
350
|
getComponentKey(xmlFile) {
|
|
326
351
|
var _a, _b;
|
|
327
352
|
return ((_b = (_a = xmlFile.componentName) === null || _a === void 0 ? void 0 : _a.text) !== null && _b !== void 0 ? _b : xmlFile.pkgPath).toLowerCase();
|
|
328
353
|
}
|
|
329
354
|
/**
|
|
330
|
-
*
|
|
355
|
+
* Resolves symbol table with the first component in this.components to have the same name as the component in the file
|
|
331
356
|
* @param componentKey key getting a component from `this.components`
|
|
332
357
|
* @param componentName the unprefixed name of the component that will be added (e.g. 'MyLabel' NOT 'roSgNodeMyLabel')
|
|
333
358
|
*/
|
|
@@ -337,18 +362,53 @@ class Program {
|
|
|
337
362
|
return;
|
|
338
363
|
}
|
|
339
364
|
const components = this.components[componentKey] || [];
|
|
365
|
+
const previousComponentType = this.componentsTable.getSymbolType(symbolName, { flags: 2 /* SymbolTypeFlag.typetime */ });
|
|
340
366
|
// Remove any existing symbols that match
|
|
341
|
-
this.
|
|
342
|
-
// There is a component that can be added - use it.
|
|
367
|
+
this.componentsTable.removeSymbol(symbolName);
|
|
343
368
|
if (components.length > 0) {
|
|
369
|
+
// There is a component that can be added - use it.
|
|
344
370
|
const componentScope = components[0].scope;
|
|
345
|
-
|
|
346
|
-
|
|
371
|
+
this.componentsTable.removeSymbol(symbolName);
|
|
372
|
+
componentScope.linkSymbolTable();
|
|
347
373
|
const componentType = componentScope.getComponentType();
|
|
348
374
|
if (componentType) {
|
|
349
|
-
this.
|
|
375
|
+
this.componentsTable.addSymbol(symbolName, {}, componentType, 2 /* SymbolTypeFlag.typetime */);
|
|
376
|
+
}
|
|
377
|
+
const typeData = {};
|
|
378
|
+
const isSameAsPrevious = previousComponentType && componentType.isEqual(previousComponentType, typeData);
|
|
379
|
+
const isComponentTypeDifferent = !previousComponentType || (0, reflection_1.isReferenceType)(previousComponentType) || !isSameAsPrevious;
|
|
380
|
+
componentScope.unlinkSymbolTable();
|
|
381
|
+
return isComponentTypeDifferent;
|
|
382
|
+
}
|
|
383
|
+
// There was a previous component type, but no new one, so it's different
|
|
384
|
+
return !!previousComponentType;
|
|
385
|
+
}
|
|
386
|
+
/**
|
|
387
|
+
* Adds a reference type to the global symbol table with the first component in this.components to have the same name as the component in the file
|
|
388
|
+
* This is so on a first validation, these types can be resolved in teh future (eg. when the actual component is created)
|
|
389
|
+
* If we don't add reference types at this top level, they will be created at the file level, and will never get resolved
|
|
390
|
+
* @param componentKey key getting a component from `this.components`
|
|
391
|
+
* @param componentName the unprefixed name of the component that will be added (e.g. 'MyLabel' NOT 'roSgNodeMyLabel')
|
|
392
|
+
*/
|
|
393
|
+
addComponentReferenceType(componentKey, componentName) {
|
|
394
|
+
const symbolName = componentName ? util_1.util.getSgNodeTypeName(componentName) : undefined;
|
|
395
|
+
if (!symbolName) {
|
|
396
|
+
return;
|
|
397
|
+
}
|
|
398
|
+
const components = this.components[componentKey] || [];
|
|
399
|
+
if (components.length > 0) {
|
|
400
|
+
// There is a component that can be added,
|
|
401
|
+
if (!this.componentsTable.hasSymbol(symbolName, 2 /* SymbolTypeFlag.typetime */)) {
|
|
402
|
+
// it doesn't already exist in the table
|
|
403
|
+
const componentRefType = new types_1.ReferenceType(symbolName, symbolName, 2 /* SymbolTypeFlag.typetime */, () => this.componentsTable);
|
|
404
|
+
if (componentRefType) {
|
|
405
|
+
this.componentsTable.addSymbol(symbolName, {}, componentRefType, 2 /* SymbolTypeFlag.typetime */);
|
|
406
|
+
}
|
|
350
407
|
}
|
|
351
|
-
|
|
408
|
+
}
|
|
409
|
+
else {
|
|
410
|
+
// there is no component. remove from table
|
|
411
|
+
this.componentsTable.removeSymbol(symbolName);
|
|
352
412
|
}
|
|
353
413
|
}
|
|
354
414
|
/**
|
|
@@ -514,7 +574,7 @@ class Program {
|
|
|
514
574
|
//create a new scope for this xml file
|
|
515
575
|
let scope = new XmlScope_1.XmlScope(file, this);
|
|
516
576
|
this.addScope(scope);
|
|
517
|
-
//register this
|
|
577
|
+
//register this componet now that we have parsed it and know its component name
|
|
518
578
|
this.registerComponent(file, scope);
|
|
519
579
|
//notify plugins that the scope is created and the component is registered
|
|
520
580
|
this.plugins.emit('afterScopeCreate', {
|
|
@@ -642,6 +702,7 @@ class Program {
|
|
|
642
702
|
//if there is a scope named the same as this file's path, remove it (i.e. xml scopes)
|
|
643
703
|
let scope = this.scopes[file.destPath];
|
|
644
704
|
if (scope) {
|
|
705
|
+
this.logger.debug('Removing associated scope', scope.name);
|
|
645
706
|
const scopeDisposeEvent = {
|
|
646
707
|
program: this,
|
|
647
708
|
scope: scope
|
|
@@ -662,6 +723,7 @@ class Program {
|
|
|
662
723
|
this.dependencyGraph.removeDependency('scope:source', file.dependencyGraphKey);
|
|
663
724
|
}
|
|
664
725
|
if ((0, reflection_1.isBrsFile)(file)) {
|
|
726
|
+
this.logger.debug('Removing file symbol info', file.srcPath);
|
|
665
727
|
if (!keepSymbolInformation) {
|
|
666
728
|
this.fileSymbolInformation.delete(file.pkgPath);
|
|
667
729
|
}
|
|
@@ -669,8 +731,10 @@ class Program {
|
|
|
669
731
|
}
|
|
670
732
|
//if this is a component, remove it from our components map
|
|
671
733
|
if ((0, reflection_1.isXmlFile)(file)) {
|
|
734
|
+
this.logger.debug('Unregistering component', file.srcPath);
|
|
672
735
|
this.unregisterComponent(file);
|
|
673
736
|
}
|
|
737
|
+
this.logger.debug('Disposing file', file.srcPath);
|
|
674
738
|
//dispose any disposable things on the file
|
|
675
739
|
for (const disposable of (_c = file === null || file === void 0 ? void 0 : file.disposables) !== null && _c !== void 0 ? _c : []) {
|
|
676
740
|
disposable();
|
|
@@ -697,18 +761,43 @@ class Program {
|
|
|
697
761
|
fileValidationTime: '',
|
|
698
762
|
crossScopeValidationTime: '',
|
|
699
763
|
scopesValidated: 0,
|
|
764
|
+
changedSymbols: 0,
|
|
700
765
|
totalLinkTime: '',
|
|
701
766
|
totalScopeValidationTime: '',
|
|
702
|
-
componentValidationTime: ''
|
|
767
|
+
componentValidationTime: '',
|
|
768
|
+
changedSymbolsTime: ''
|
|
703
769
|
};
|
|
704
770
|
const validationStopwatch = new Stopwatch_1.Stopwatch();
|
|
705
771
|
//validate every file
|
|
706
772
|
const brsFilesValidated = [];
|
|
773
|
+
const xmlFilesValidated = [];
|
|
707
774
|
const afterValidateFiles = [];
|
|
775
|
+
const sortedFiles = Object.values(this.files).sort((0, thenby_1.firstBy)(x => x.srcPath));
|
|
776
|
+
this.logger.time(logging_1.LogLevel.info, ['Prebuild component types'], () => {
|
|
777
|
+
// cast a wide net for potential changes in components
|
|
778
|
+
for (const file of sortedFiles) {
|
|
779
|
+
if (file.isValidated) {
|
|
780
|
+
continue;
|
|
781
|
+
}
|
|
782
|
+
if ((0, reflection_1.isXmlFile)(file)) {
|
|
783
|
+
this.addDeferredComponentTypeSymbolCreation(file);
|
|
784
|
+
}
|
|
785
|
+
else if ((0, reflection_1.isBrsFile)(file)) {
|
|
786
|
+
for (const scope of this.getScopesForFile(file)) {
|
|
787
|
+
if ((0, reflection_1.isXmlScope)(scope)) {
|
|
788
|
+
this.addDeferredComponentTypeSymbolCreation(scope.xmlFile);
|
|
789
|
+
}
|
|
790
|
+
}
|
|
791
|
+
}
|
|
792
|
+
}
|
|
793
|
+
// Create reference component types for any component that changes
|
|
794
|
+
for (let [componentKey, componentName] of this.componentSymbolsToUpdate.entries()) {
|
|
795
|
+
this.addComponentReferenceType(componentKey, componentName);
|
|
796
|
+
}
|
|
797
|
+
});
|
|
708
798
|
metrics.fileValidationTime = validationStopwatch.getDurationTextFor(() => {
|
|
709
799
|
//sort files by path so we get consistent results
|
|
710
|
-
const
|
|
711
|
-
for (const file of files) {
|
|
800
|
+
for (const file of sortedFiles) {
|
|
712
801
|
//for every unvalidated file, validate it
|
|
713
802
|
if (!file.isValidated) {
|
|
714
803
|
const validateFileEvent = {
|
|
@@ -722,6 +811,9 @@ class Program {
|
|
|
722
811
|
if ((0, reflection_1.isBrsFile)(file)) {
|
|
723
812
|
brsFilesValidated.push(file);
|
|
724
813
|
}
|
|
814
|
+
else if ((0, reflection_1.isXmlFile)(file)) {
|
|
815
|
+
xmlFilesValidated.push(file);
|
|
816
|
+
}
|
|
725
817
|
afterValidateFiles.push(file);
|
|
726
818
|
}
|
|
727
819
|
}
|
|
@@ -735,27 +827,88 @@ class Program {
|
|
|
735
827
|
}
|
|
736
828
|
}).durationText;
|
|
737
829
|
metrics.filesChanged = afterValidateFiles.length;
|
|
830
|
+
const changedComponentTypes = [];
|
|
738
831
|
// Build component types for any component that changes
|
|
739
832
|
this.logger.time(logging_1.LogLevel.info, ['Build component types'], () => {
|
|
740
|
-
for (let
|
|
741
|
-
this.updateComponentSymbolInGlobalScope(componentKey, componentName)
|
|
833
|
+
for (let [componentKey, componentName] of this.componentSymbolsToUpdate.entries()) {
|
|
834
|
+
if (this.updateComponentSymbolInGlobalScope(componentKey, componentName)) {
|
|
835
|
+
changedComponentTypes.push(util_1.util.getSgNodeTypeName(componentName).toLowerCase());
|
|
836
|
+
}
|
|
742
837
|
}
|
|
743
838
|
this.componentSymbolsToUpdate.clear();
|
|
744
839
|
});
|
|
745
|
-
|
|
746
|
-
if ((0, reflection_1.isBrsFile)(f)) {
|
|
747
|
-
return f.providedSymbols.changes;
|
|
748
|
-
}
|
|
749
|
-
return null;
|
|
750
|
-
}).filter(x => x);
|
|
840
|
+
// get set of changed symbols
|
|
751
841
|
const changedSymbols = new Map();
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
842
|
+
metrics.changedSymbolsTime = validationStopwatch.getDurationTextFor(() => {
|
|
843
|
+
var _a, _b, _c, _d;
|
|
844
|
+
const changedSymbolsMapArr = (_a = [...brsFilesValidated, ...xmlFilesValidated]) === null || _a === void 0 ? void 0 : _a.map(f => {
|
|
845
|
+
if ((0, reflection_1.isBrsFile)(f)) {
|
|
846
|
+
return f.providedSymbols.changes;
|
|
847
|
+
}
|
|
848
|
+
return null;
|
|
849
|
+
}).filter(x => x);
|
|
850
|
+
// update the map of typetime dependencies
|
|
851
|
+
for (const file of brsFilesValidated) {
|
|
852
|
+
for (const [symbolName, provided] of file.providedSymbols.symbolMap.get(2 /* SymbolTypeFlag.typetime */).entries()) {
|
|
853
|
+
// clear existing dependencies
|
|
854
|
+
for (const values of this.symbolDependencies.values()) {
|
|
855
|
+
values.delete(symbolName);
|
|
856
|
+
}
|
|
857
|
+
// map types to the set of types that depend upon them
|
|
858
|
+
for (const dependentSymbol of (_c = (_b = provided.requiredSymbolNames) === null || _b === void 0 ? void 0 : _b.values()) !== null && _c !== void 0 ? _c : []) {
|
|
859
|
+
const dependentSymbolLower = dependentSymbol.toLowerCase();
|
|
860
|
+
if (!this.symbolDependencies.has(dependentSymbolLower)) {
|
|
861
|
+
this.symbolDependencies.set(dependentSymbolLower, new Set());
|
|
862
|
+
}
|
|
863
|
+
const symbolsDependentUpon = this.symbolDependencies.get(dependentSymbolLower);
|
|
864
|
+
symbolsDependentUpon.add(symbolName);
|
|
865
|
+
}
|
|
866
|
+
}
|
|
867
|
+
}
|
|
868
|
+
for (const flag of [1 /* SymbolTypeFlag.runtime */, 2 /* SymbolTypeFlag.typetime */]) {
|
|
869
|
+
const changedSymbolsSetArr = changedSymbolsMapArr.map(symMap => symMap.get(flag));
|
|
870
|
+
const changedSymbolSet = new Set();
|
|
871
|
+
for (const changeSet of changedSymbolsSetArr) {
|
|
872
|
+
for (const change of changeSet) {
|
|
873
|
+
changedSymbolSet.add(change);
|
|
874
|
+
}
|
|
875
|
+
}
|
|
876
|
+
changedSymbols.set(flag, changedSymbolSet);
|
|
877
|
+
}
|
|
878
|
+
// update changed symbol set with any changed component
|
|
879
|
+
for (const changedComponentType of changedComponentTypes) {
|
|
880
|
+
changedSymbols.get(2 /* SymbolTypeFlag.typetime */).add(changedComponentType);
|
|
881
|
+
}
|
|
882
|
+
// Add any additional types that depend on a changed type
|
|
883
|
+
// as each iteration of the loop might add new types, need to keep checking until nothing new is added
|
|
884
|
+
const dependentTypesChanged = new Set();
|
|
885
|
+
let foundDependentTypes = false;
|
|
886
|
+
const changedTypeSymbols = changedSymbols.get(2 /* SymbolTypeFlag.typetime */);
|
|
887
|
+
do {
|
|
888
|
+
foundDependentTypes = false;
|
|
889
|
+
const allChangedTypesSofar = [...Array.from(changedTypeSymbols), ...Array.from(dependentTypesChanged)];
|
|
890
|
+
for (const changedSymbol of allChangedTypesSofar) {
|
|
891
|
+
const symbolsDependentUponChangedSymbol = (_d = this.symbolDependencies.get(changedSymbol)) !== null && _d !== void 0 ? _d : [];
|
|
892
|
+
for (const symbolName of symbolsDependentUponChangedSymbol) {
|
|
893
|
+
if (!changedTypeSymbols.has(symbolName) && !dependentTypesChanged.has(symbolName)) {
|
|
894
|
+
foundDependentTypes = true;
|
|
895
|
+
dependentTypesChanged.add(symbolName);
|
|
896
|
+
}
|
|
897
|
+
}
|
|
898
|
+
}
|
|
899
|
+
} while (foundDependentTypes);
|
|
900
|
+
changedSymbols.set(2 /* SymbolTypeFlag.typetime */, new Set([...changedTypeSymbols, ...dependentTypesChanged]));
|
|
901
|
+
}).durationText;
|
|
902
|
+
if (this.options.logLevel === logging_1.LogLevel.debug) {
|
|
903
|
+
const changedRuntime = Array.from(changedSymbols.get(1 /* SymbolTypeFlag.runtime */)).sort();
|
|
904
|
+
this.logger.debug('Changed Symbols (runTime):', changedRuntime.join(', '));
|
|
905
|
+
const changedTypetime = Array.from(changedSymbols.get(2 /* SymbolTypeFlag.typetime */)).sort();
|
|
906
|
+
this.logger.debug('Changed Symbols (typeTime):', changedTypetime.join(', '));
|
|
755
907
|
}
|
|
908
|
+
metrics.changedSymbols = changedSymbols.get(1 /* SymbolTypeFlag.runtime */).size + changedSymbols.get(2 /* SymbolTypeFlag.typetime */).size;
|
|
756
909
|
const filesToBeValidatedInScopeContext = new Set(afterValidateFiles);
|
|
757
910
|
metrics.crossScopeValidationTime = validationStopwatch.getDurationTextFor(() => {
|
|
758
|
-
const scopesToCheck = this.getScopesForCrossScopeValidation();
|
|
911
|
+
const scopesToCheck = this.getScopesForCrossScopeValidation(changedComponentTypes.length > 0);
|
|
759
912
|
this.crossScopeValidation.buildComponentsMap();
|
|
760
913
|
this.crossScopeValidation.addDiagnosticsForScopes(scopesToCheck);
|
|
761
914
|
const filesToRevalidate = this.crossScopeValidation.getFilesRequiringChangedSymbol(scopesToCheck, changedSymbols);
|
|
@@ -768,22 +921,26 @@ class Program {
|
|
|
768
921
|
let validationTime = 0;
|
|
769
922
|
let scopesValidated = 0;
|
|
770
923
|
let changedFiles = new Set(afterValidateFiles);
|
|
924
|
+
this.currentScopeValidationOptions = {
|
|
925
|
+
filesToBeValidatedInScopeContext: filesToBeValidatedInScopeContext,
|
|
926
|
+
changedSymbols: changedSymbols,
|
|
927
|
+
changedFiles: changedFiles,
|
|
928
|
+
initialValidation: this.isFirstValidation
|
|
929
|
+
};
|
|
771
930
|
this.logger.time(logging_1.LogLevel.info, ['Validate all scopes'], () => {
|
|
772
931
|
//sort the scope names so we get consistent results
|
|
773
932
|
const scopeNames = this.getSortedScopeNames();
|
|
774
933
|
for (const file of filesToBeValidatedInScopeContext) {
|
|
775
934
|
if ((0, reflection_1.isBrsFile)(file)) {
|
|
776
935
|
file.validationSegmenter.unValidateAllSegments();
|
|
936
|
+
for (const scope of this.getScopesForFile(file)) {
|
|
937
|
+
scope.invalidate();
|
|
938
|
+
}
|
|
777
939
|
}
|
|
778
940
|
}
|
|
779
941
|
for (let scopeName of scopeNames) {
|
|
780
942
|
let scope = this.scopes[scopeName];
|
|
781
|
-
const scopeValidated = scope.validate(
|
|
782
|
-
filesToBeValidatedInScopeContext: filesToBeValidatedInScopeContext,
|
|
783
|
-
changedSymbols: changedSymbols,
|
|
784
|
-
changedFiles: changedFiles,
|
|
785
|
-
initialValidation: this.isFirstValidation
|
|
786
|
-
});
|
|
943
|
+
const scopeValidated = scope.validate(this.currentScopeValidationOptions);
|
|
787
944
|
if (scopeValidated) {
|
|
788
945
|
scopesValidated++;
|
|
789
946
|
}
|
|
@@ -812,11 +969,11 @@ class Program {
|
|
|
812
969
|
}
|
|
813
970
|
this.logger.info(`Validation Metrics: ${logs.join(', ')}`);
|
|
814
971
|
}
|
|
815
|
-
getScopesForCrossScopeValidation() {
|
|
972
|
+
getScopesForCrossScopeValidation(someComponentTypeChanged = false) {
|
|
816
973
|
const scopesForCrossScopeValidation = [];
|
|
817
974
|
for (let scopeName of this.getSortedScopeNames()) {
|
|
818
975
|
let scope = this.scopes[scopeName];
|
|
819
|
-
if (this.globalScope !== scope && !scope.isValidated) {
|
|
976
|
+
if (this.globalScope !== scope && (someComponentTypeChanged || !scope.isValidated)) {
|
|
820
977
|
scopesForCrossScopeValidation.push(scope);
|
|
821
978
|
}
|
|
822
979
|
}
|