brighterscript 1.0.0-alpha.15 → 1.0.0-alpha.18

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.
Files changed (163) hide show
  1. package/CHANGELOG.md +83 -0
  2. package/README.md +28 -9
  3. package/dist/DependencyGraph.js +5 -4
  4. package/dist/DependencyGraph.js.map +1 -1
  5. package/dist/DiagnosticMessages.d.ts +16 -1
  6. package/dist/DiagnosticMessages.js +15 -0
  7. package/dist/DiagnosticMessages.js.map +1 -1
  8. package/dist/Logger.js +5 -5
  9. package/dist/Logger.js.map +1 -1
  10. package/dist/Program.d.ts +2 -2
  11. package/dist/Program.js +5 -3
  12. package/dist/Program.js.map +1 -1
  13. package/dist/ProgramBuilder.js +1 -1
  14. package/dist/ProgramBuilder.js.map +1 -1
  15. package/dist/Scope.d.ts +58 -8
  16. package/dist/Scope.js +142 -23
  17. package/dist/Scope.js.map +1 -1
  18. package/dist/XmlScope.js +1 -1
  19. package/dist/XmlScope.js.map +1 -1
  20. package/dist/astUtils/creators.d.ts +10 -6
  21. package/dist/astUtils/creators.js +93 -12
  22. package/dist/astUtils/creators.js.map +1 -1
  23. package/dist/astUtils/creators.spec.js +10 -0
  24. package/dist/astUtils/creators.spec.js.map +1 -1
  25. package/dist/astUtils/reflection.d.ts +8 -3
  26. package/dist/astUtils/reflection.js +18 -2
  27. package/dist/astUtils/reflection.js.map +1 -1
  28. package/dist/astUtils/reflection.spec.js +15 -4
  29. package/dist/astUtils/reflection.spec.js.map +1 -1
  30. package/dist/astUtils/visitors.d.ts +4 -1
  31. package/dist/astUtils/visitors.js.map +1 -1
  32. package/dist/astUtils/visitors.spec.js +2 -0
  33. package/dist/astUtils/visitors.spec.js.map +1 -1
  34. package/dist/bscPlugin/semanticTokens/BrsFileSemanticTokensProcessor.js +2 -2
  35. package/dist/bscPlugin/semanticTokens/BrsFileSemanticTokensProcessor.js.map +1 -1
  36. package/dist/bscPlugin/transpile/BrsFilePreTranspileProcessor.js +7 -3
  37. package/dist/bscPlugin/transpile/BrsFilePreTranspileProcessor.js.map +1 -1
  38. package/dist/{types/FunctionType.spec.d.ts → bscPlugin/transpile/BrsFilePreTranspileProcessor.spec.d.ts} +0 -0
  39. package/dist/bscPlugin/transpile/BrsFilePreTranspileProcessor.spec.js +32 -0
  40. package/dist/bscPlugin/transpile/BrsFilePreTranspileProcessor.spec.js.map +1 -0
  41. package/dist/diagnosticUtils.js +3 -3
  42. package/dist/diagnosticUtils.js.map +1 -1
  43. package/dist/examples/plugins/removePrint.js +12 -14
  44. package/dist/examples/plugins/removePrint.js.map +1 -1
  45. package/dist/files/BrsFile.Class.spec.js +3 -3
  46. package/dist/files/BrsFile.Class.spec.js.map +1 -1
  47. package/dist/files/BrsFile.d.ts +2 -2
  48. package/dist/files/BrsFile.js +99 -63
  49. package/dist/files/BrsFile.js.map +1 -1
  50. package/dist/files/BrsFile.spec.js +187 -67
  51. package/dist/files/BrsFile.spec.js.map +1 -1
  52. package/dist/files/XmlFile.js +3 -3
  53. package/dist/files/XmlFile.js.map +1 -1
  54. package/dist/globalCallables.js +79 -79
  55. package/dist/globalCallables.js.map +1 -1
  56. package/dist/interfaces.d.ts +43 -4
  57. package/dist/parser/Expression.d.ts +91 -22
  58. package/dist/parser/Expression.js +191 -57
  59. package/dist/parser/Expression.js.map +1 -1
  60. package/dist/parser/Parser.Class.spec.js +6 -6
  61. package/dist/parser/Parser.Class.spec.js.map +1 -1
  62. package/dist/parser/Parser.d.ts +3 -6
  63. package/dist/parser/Parser.js +166 -155
  64. package/dist/parser/Parser.js.map +1 -1
  65. package/dist/parser/Parser.spec.js +61 -6
  66. package/dist/parser/Parser.spec.js.map +1 -1
  67. package/dist/parser/SGTypes.d.ts +2 -2
  68. package/dist/parser/SGTypes.js +2 -2
  69. package/dist/parser/SGTypes.js.map +1 -1
  70. package/dist/parser/Statement.d.ts +85 -57
  71. package/dist/parser/Statement.js +228 -173
  72. package/dist/parser/Statement.js.map +1 -1
  73. package/dist/parser/tests/statement/For.spec.d.ts +1 -0
  74. package/dist/parser/tests/statement/For.spec.js +46 -0
  75. package/dist/parser/tests/statement/For.spec.js.map +1 -0
  76. package/dist/parser/tests/statement/ForEach.spec.d.ts +1 -0
  77. package/dist/parser/tests/statement/ForEach.spec.js +37 -0
  78. package/dist/parser/tests/statement/ForEach.spec.js.map +1 -0
  79. package/dist/parser/tests/statement/InterfaceStatement.spec.js +181 -0
  80. package/dist/parser/tests/statement/InterfaceStatement.spec.js.map +1 -1
  81. package/dist/parser/tests/statement/TryCatch.spec.js +7 -5
  82. package/dist/parser/tests/statement/TryCatch.spec.js.map +1 -1
  83. package/dist/types/ArrayType.js +4 -1
  84. package/dist/types/ArrayType.js.map +1 -1
  85. package/dist/types/ArrayType.spec.js +3 -1
  86. package/dist/types/ArrayType.spec.js.map +1 -1
  87. package/dist/types/BooleanType.d.ts +4 -2
  88. package/dist/types/BooleanType.js +7 -2
  89. package/dist/types/BooleanType.js.map +1 -1
  90. package/dist/types/BooleanType.spec.js +3 -1
  91. package/dist/types/BooleanType.spec.js.map +1 -1
  92. package/dist/types/BscType.d.ts +1 -0
  93. package/dist/types/BscType.js +16 -1
  94. package/dist/types/BscType.js.map +1 -1
  95. package/dist/types/CustomType.js +10 -0
  96. package/dist/types/CustomType.js.map +1 -1
  97. package/dist/types/DoubleType.d.ts +2 -0
  98. package/dist/types/DoubleType.js +7 -2
  99. package/dist/types/DoubleType.js.map +1 -1
  100. package/dist/types/DoubleType.spec.js +3 -1
  101. package/dist/types/DoubleType.spec.js.map +1 -1
  102. package/dist/types/DynamicType.d.ts +2 -0
  103. package/dist/types/DynamicType.js +5 -1
  104. package/dist/types/DynamicType.js.map +1 -1
  105. package/dist/types/FloatType.d.ts +3 -1
  106. package/dist/types/FloatType.js +7 -2
  107. package/dist/types/FloatType.js.map +1 -1
  108. package/dist/types/FloatType.spec.js +2 -0
  109. package/dist/types/FloatType.spec.js.map +1 -1
  110. package/dist/types/FunctionType.d.ts +3 -21
  111. package/dist/types/FunctionType.js +8 -65
  112. package/dist/types/FunctionType.js.map +1 -1
  113. package/dist/types/IntegerType.d.ts +3 -1
  114. package/dist/types/IntegerType.js +7 -2
  115. package/dist/types/IntegerType.js.map +1 -1
  116. package/dist/types/IntegerType.spec.js +3 -1
  117. package/dist/types/IntegerType.spec.js.map +1 -1
  118. package/dist/types/InterfaceType.d.ts +13 -10
  119. package/dist/types/InterfaceType.js +33 -29
  120. package/dist/types/InterfaceType.js.map +1 -1
  121. package/dist/types/InterfaceType.spec.js +36 -16
  122. package/dist/types/InterfaceType.spec.js.map +1 -1
  123. package/dist/types/InvalidType.d.ts +4 -2
  124. package/dist/types/InvalidType.js +7 -2
  125. package/dist/types/InvalidType.js.map +1 -1
  126. package/dist/types/InvalidType.spec.js +2 -0
  127. package/dist/types/InvalidType.spec.js.map +1 -1
  128. package/dist/types/LazyType.js +4 -0
  129. package/dist/types/LazyType.js.map +1 -1
  130. package/dist/types/LongIntegerType.d.ts +3 -1
  131. package/dist/types/LongIntegerType.js +7 -2
  132. package/dist/types/LongIntegerType.js.map +1 -1
  133. package/dist/types/LongIntegerType.spec.js +2 -0
  134. package/dist/types/LongIntegerType.spec.js.map +1 -1
  135. package/dist/types/ObjectType.d.ts +2 -1
  136. package/dist/types/ObjectType.js +4 -2
  137. package/dist/types/ObjectType.js.map +1 -1
  138. package/dist/types/StringType.d.ts +4 -2
  139. package/dist/types/StringType.js +7 -2
  140. package/dist/types/StringType.js.map +1 -1
  141. package/dist/types/StringType.spec.js +2 -0
  142. package/dist/types/StringType.spec.js.map +1 -1
  143. package/dist/types/TypedFunctionType.d.ts +28 -0
  144. package/dist/types/TypedFunctionType.js +88 -0
  145. package/dist/types/TypedFunctionType.js.map +1 -0
  146. package/dist/types/TypedFunctionType.spec.d.ts +1 -0
  147. package/dist/types/TypedFunctionType.spec.js +37 -0
  148. package/dist/types/TypedFunctionType.spec.js.map +1 -0
  149. package/dist/types/UninitializedType.js.map +1 -1
  150. package/dist/types/VoidType.d.ts +4 -2
  151. package/dist/types/VoidType.js +5 -1
  152. package/dist/types/VoidType.js.map +1 -1
  153. package/dist/types/helpers.js +7 -2
  154. package/dist/types/helpers.js.map +1 -1
  155. package/dist/util.d.ts +2 -2
  156. package/dist/util.js +39 -46
  157. package/dist/util.js.map +1 -1
  158. package/dist/validators/ClassValidator.d.ts +14 -1
  159. package/dist/validators/ClassValidator.js +129 -82
  160. package/dist/validators/ClassValidator.js.map +1 -1
  161. package/package.json +2 -3
  162. package/dist/types/FunctionType.spec.js +0 -29
  163. package/dist/types/FunctionType.spec.js.map +0 -1
@@ -187,7 +187,7 @@ class Parser {
187
187
  declaration() {
188
188
  try {
189
189
  if (this.checkAny(TokenKind_1.TokenKind.Sub, TokenKind_1.TokenKind.Function)) {
190
- return this.functionDeclaration(false);
190
+ return this.functionStatement({ hasName: true, hasBody: true, hasEnd: true });
191
191
  }
192
192
  if (this.checkLibrary()) {
193
193
  return this.libraryStatement();
@@ -230,56 +230,40 @@ class Parser {
230
230
  return identifier;
231
231
  }
232
232
  enumMemberStatement() {
233
- const statement = new Statement_1.EnumMemberStatement({});
234
- statement.tokens.name = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedClassFieldIdentifier(), TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties);
233
+ const tokens = {};
234
+ let value;
235
+ tokens.name = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedClassFieldIdentifier(), TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties);
235
236
  //look for `= SOME_EXPRESSION`
236
237
  if (this.check(TokenKind_1.TokenKind.Equal)) {
237
- statement.tokens.equal = this.advance();
238
- statement.value = this.expression();
238
+ tokens.equal = this.advance();
239
+ value = this.expression();
239
240
  }
240
- return statement;
241
+ return new Statement_1.EnumMemberStatement(tokens, value);
241
242
  }
242
243
  /**
243
- * Create a new InterfaceMethodStatement. This should only be called from within `interfaceDeclaration`
244
+ * Create a new InterfaceFieldStatement. This should only be called from within `interfaceDeclaration`
244
245
  */
245
246
  interfaceFieldStatement() {
246
247
  const name = this.identifier(...TokenKind_1.AllowedProperties);
247
- let asToken = this.consumeToken(TokenKind_1.TokenKind.As);
248
- let typeToken = this.typeToken();
249
- const type = util_1.util.tokenToBscType(typeToken);
250
- if (!type) {
251
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionParameterTypeIsInvalid(name.text, typeToken.text)), { range: typeToken.range }));
252
- throw this.lastDiagnosticAsError();
253
- }
254
- return new Statement_1.InterfaceFieldStatement(name, asToken, typeToken, type);
255
- }
256
- /**
257
- * Create a new InterfaceMethodStatement. This should only be called from within `interfaceDeclaration()`
258
- */
259
- interfaceMethodStatement() {
260
- const functionType = this.advance();
261
- const name = this.identifier(...TokenKind_1.AllowedProperties);
262
- const leftParen = this.consumeToken(TokenKind_1.TokenKind.LeftParen);
263
- const params = [];
264
- const rightParen = this.consumeToken(TokenKind_1.TokenKind.RightParen);
265
- let asToken = null;
266
- let returnTypeToken = null;
248
+ let asToken;
249
+ let typeExpr;
250
+ //look for `as SOME_TYPE`
267
251
  if (this.check(TokenKind_1.TokenKind.As)) {
268
- asToken = this.advance();
269
- returnTypeToken = this.typeToken();
270
- const returnType = util_1.util.tokenToBscType(returnTypeToken);
271
- if (!returnType) {
272
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionParameterTypeIsInvalid(name.text, returnTypeToken.text)), { range: returnTypeToken.range }));
273
- throw this.lastDiagnosticAsError();
252
+ asToken = this.consumeToken(TokenKind_1.TokenKind.As);
253
+ typeExpr = this.typeExpression();
254
+ //no field type specified
255
+ if (!typeExpr.isValidType()) {
256
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionParameterTypeIsInvalid(name.text, typeExpr.getText())), { range: typeExpr.range }));
274
257
  }
275
258
  }
276
- return new Statement_1.InterfaceMethodStatement(functionType, name, leftParen, params, rightParen, asToken, returnTypeToken, util_1.util.tokenToBscType(returnTypeToken));
259
+ return new Statement_1.InterfaceFieldStatement(name, asToken, typeExpr, this.currentNamespaceName);
277
260
  }
278
261
  interfaceDeclaration() {
279
262
  this.warnIfNotBrighterScriptMode('interface declarations');
280
263
  const parentAnnotations = this.enterAnnotationBlock();
281
264
  const interfaceToken = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedKeyword(TokenKind_1.TokenKind.Interface), TokenKind_1.TokenKind.Interface);
282
- const nameToken = this.identifier(...this.allowedLocalIdentifiers);
265
+ //get the interface name
266
+ let nameToken = this.tryConsume(DiagnosticMessages_1.DiagnosticMessages.expectedIdentifierAfterKeyword('interface'), TokenKind_1.TokenKind.Identifier, ...this.allowedLocalIdentifiers);
283
267
  let extendsToken;
284
268
  let parentInterfaceName;
285
269
  if (this.peek().text.toLowerCase() === 'extends') {
@@ -291,6 +275,10 @@ class Parser {
291
275
  let body = [];
292
276
  while (this.checkAny(TokenKind_1.TokenKind.Comment, TokenKind_1.TokenKind.Identifier, TokenKind_1.TokenKind.At, ...TokenKind_1.AllowedProperties)) {
293
277
  try {
278
+ //break out of this loop if we encountered the `EndInterface` token not followed by `as`
279
+ if (this.check(TokenKind_1.TokenKind.EndInterface) && !this.checkNext(TokenKind_1.TokenKind.As)) {
280
+ break;
281
+ }
294
282
  let decl;
295
283
  //collect leading annotations
296
284
  if (this.check(TokenKind_1.TokenKind.At)) {
@@ -302,7 +290,15 @@ class Parser {
302
290
  //methods (function/sub keyword followed by opening paren)
303
291
  }
304
292
  else if (this.checkAny(TokenKind_1.TokenKind.Function, TokenKind_1.TokenKind.Sub) && this.checkAny(TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties)) {
305
- decl = this.interfaceMethodStatement();
293
+ const functionStatement = this.functionStatement({
294
+ hasName: true,
295
+ hasBody: false,
296
+ hasEnd: false,
297
+ onlyCallableAsMember: true
298
+ });
299
+ decl = new Statement_1.InterfaceMethodStatement(functionStatement.name, functionStatement.func);
300
+ //refer to this statement as parent of the expression
301
+ functionStatement.func.functionStatement = decl;
306
302
  //comments
307
303
  }
308
304
  else if (this.check(TokenKind_1.TokenKind.Comment)) {
@@ -312,10 +308,6 @@ class Parser {
312
308
  this.consumePendingAnnotations(decl);
313
309
  body.push(decl);
314
310
  }
315
- else {
316
- //we didn't find a declaration...flag tokens until next line
317
- this.flagUntil(TokenKind_1.TokenKind.Newline, TokenKind_1.TokenKind.Colon, TokenKind_1.TokenKind.Eof);
318
- }
319
311
  }
320
312
  catch (e) {
321
313
  //throw out any failed members and move on to the next line
@@ -323,24 +315,24 @@ class Parser {
323
315
  }
324
316
  //ensure statement separator
325
317
  this.consumeStatementSeparators();
326
- //break out of this loop if we encountered the `EndInterface` token not followed by `as`
327
- if (this.check(TokenKind_1.TokenKind.EndInterface) && !this.checkNext(TokenKind_1.TokenKind.As)) {
328
- break;
329
- }
330
318
  }
331
319
  //consume the final `end interface` token
332
- const endInterfaceToken = this.consumeToken(TokenKind_1.TokenKind.EndInterface);
333
- const statement = new Statement_1.InterfaceStatement(interfaceToken, nameToken, extendsToken, parentInterfaceName, body, endInterfaceToken, this.currentNamespaceName);
320
+ let endingKeyword = this.advance();
321
+ if (endingKeyword.kind !== TokenKind_1.TokenKind.EndInterface) {
322
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.couldNotFindMatchingEndKeyword('interface')), { range: endingKeyword.range }));
323
+ }
324
+ const statement = new Statement_1.InterfaceStatement(interfaceToken, nameToken, extendsToken, parentInterfaceName, body, endingKeyword, this.currentNamespaceName);
334
325
  this._references.interfaceStatements.push(statement);
335
326
  this.exitAnnotationBlock(parentAnnotations);
336
327
  return statement;
337
328
  }
338
329
  enumDeclaration() {
339
- const result = new Statement_1.EnumStatement({}, [], this.currentNamespaceName);
340
330
  this.warnIfNotBrighterScriptMode('enum declarations');
341
331
  const parentAnnotations = this.enterAnnotationBlock();
342
- result.tokens.enum = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedKeyword(TokenKind_1.TokenKind.Enum), TokenKind_1.TokenKind.Enum);
343
- result.tokens.name = this.tryIdentifier();
332
+ const tokens = {};
333
+ const body = [];
334
+ tokens.enum = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedKeyword(TokenKind_1.TokenKind.Enum), TokenKind_1.TokenKind.Enum);
335
+ tokens.name = this.tryIdentifier();
344
336
  this.consumeStatementSeparators();
345
337
  //gather up all members
346
338
  while (this.checkAny(TokenKind_1.TokenKind.Comment, TokenKind_1.TokenKind.Identifier, TokenKind_1.TokenKind.At, ...TokenKind_1.AllowedProperties)) {
@@ -360,7 +352,7 @@ class Parser {
360
352
  }
361
353
  if (decl) {
362
354
  this.consumePendingAnnotations(decl);
363
- result.body.push(decl);
355
+ body.push(decl);
364
356
  }
365
357
  else {
366
358
  //we didn't find a declaration...flag tokens until next line
@@ -379,7 +371,8 @@ class Parser {
379
371
  }
380
372
  }
381
373
  //consume the final `end interface` token
382
- result.tokens.endEnum = this.consumeToken(TokenKind_1.TokenKind.EndEnum);
374
+ tokens.endEnum = this.consumeToken(TokenKind_1.TokenKind.EndEnum);
375
+ const result = new Statement_1.EnumStatement(tokens, body, this.currentNamespaceName);
383
376
  this._references.enumStatements.push(result);
384
377
  this.exitAnnotationBlock(parentAnnotations);
385
378
  return result;
@@ -421,16 +414,16 @@ class Parser {
421
414
  }
422
415
  //methods (function/sub keyword OR identifier followed by opening paren)
423
416
  if (this.checkAny(TokenKind_1.TokenKind.Function, TokenKind_1.TokenKind.Sub) || (this.checkAny(TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties) && this.checkNext(TokenKind_1.TokenKind.LeftParen))) {
424
- const funcDeclaration = this.functionDeclaration(false, false, true);
425
- //remove this function from the lists because it's not a callable
426
- const functionStatement = this._references.functionStatements.pop();
417
+ const functionStatement = this.functionStatement({ hasName: true, hasBody: true, hasEnd: true, onlyCallableAsMember: true });
427
418
  //if we have an overrides keyword AND this method is called 'new', that's not allowed
428
- if (overrideKeyword && funcDeclaration.name.text.toLowerCase() === 'new') {
419
+ if (overrideKeyword && functionStatement.name.text.toLowerCase() === 'new') {
429
420
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.cannotUseOverrideKeywordOnConstructorFunction()), { range: overrideKeyword.range }));
430
421
  }
431
- decl = new Statement_1.ClassMethodStatement(accessModifier, funcDeclaration.name, funcDeclaration.func, overrideKeyword);
422
+ decl = new Statement_1.ClassMethodStatement(accessModifier, functionStatement.name, functionStatement.func, overrideKeyword);
432
423
  //refer to this statement as parent of the expression
433
424
  functionStatement.func.functionStatement = decl;
425
+ //cache the range property so that plugins can't affect it
426
+ decl.cacheRange();
434
427
  //fields
435
428
  }
436
429
  else if (this.checkAny(TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties)) {
@@ -471,13 +464,13 @@ class Parser {
471
464
  classFieldDeclaration(accessModifier) {
472
465
  let name = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedClassFieldIdentifier(), TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties);
473
466
  let asToken;
474
- let fieldType;
467
+ let fieldTypeExpr;
475
468
  //look for `as SOME_TYPE`
476
469
  if (this.check(TokenKind_1.TokenKind.As)) {
477
470
  asToken = this.advance();
478
- fieldType = this.typeToken();
471
+ fieldTypeExpr = this.typeExpression();
479
472
  //no field type specified
480
- if (!util_1.util.tokenToBscType(fieldType, true, this.currentNamespaceName)) {
473
+ if (!fieldTypeExpr.isValidType(this.options.mode)) {
481
474
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.expectedValidTypeToFollowAsKeyword()), { range: this.peek().range }));
482
475
  }
483
476
  }
@@ -488,22 +481,34 @@ class Parser {
488
481
  equal = this.advance();
489
482
  initialValue = this.expression();
490
483
  }
491
- return new Statement_1.ClassFieldStatement(accessModifier, name, asToken, fieldType, equal, initialValue, this.currentNamespaceName);
484
+ return new Statement_1.ClassFieldStatement(accessModifier, name, asToken, fieldTypeExpr, equal, initialValue, this.currentNamespaceName);
492
485
  }
493
- functionDeclaration(isAnonymous, checkIdentifier = true, forClassMethod = false) {
486
+ functionStatement(options) {
487
+ options.hasName = true;
488
+ const funcResult = this.functionDeclaration(options);
489
+ if (funcResult) {
490
+ let result = new Statement_1.FunctionStatement(funcResult.name, funcResult.functionExpression, this.currentNamespaceName);
491
+ funcResult.functionExpression.functionStatement = result;
492
+ if (!options.onlyCallableAsMember) {
493
+ this._references.functionStatements.push(result);
494
+ }
495
+ return result;
496
+ }
497
+ }
498
+ functionDeclaration(options = {}) {
494
499
  var _a, _b, _c, _d;
495
500
  let previousCallExpressions = this.callExpressions;
496
501
  this.callExpressions = [];
497
502
  try {
498
503
  //track depth to help certain statements need to know if they are contained within a function body
499
504
  this.namespaceAndFunctionDepth++;
500
- let functionType;
505
+ let functionKeyword;
501
506
  if (this.checkAny(TokenKind_1.TokenKind.Sub, TokenKind_1.TokenKind.Function)) {
502
- functionType = this.advance();
507
+ functionKeyword = this.advance();
503
508
  }
504
509
  else {
505
510
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.missingCallableKeyword()), { range: this.peek().range }));
506
- functionType = {
511
+ functionKeyword = {
507
512
  isReserved: true,
508
513
  kind: TokenKind_1.TokenKind.Function,
509
514
  text: 'function',
@@ -515,30 +520,30 @@ class Parser {
515
520
  leadingWhitespace: ''
516
521
  };
517
522
  }
518
- let isSub = (functionType === null || functionType === void 0 ? void 0 : functionType.kind) === TokenKind_1.TokenKind.Sub;
519
- let functionTypeText = isSub ? 'sub' : 'function';
523
+ let isSub = (functionKeyword === null || functionKeyword === void 0 ? void 0 : functionKeyword.kind) === TokenKind_1.TokenKind.Sub;
524
+ let functionKeywordText = isSub ? 'sub' : 'function';
520
525
  let name;
521
526
  let leftParen;
522
- if (isAnonymous) {
523
- leftParen = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedLeftParenAfterCallable(functionTypeText), TokenKind_1.TokenKind.LeftParen);
527
+ if (!options.hasName) {
528
+ leftParen = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedLeftParenAfterCallable(functionKeywordText), TokenKind_1.TokenKind.LeftParen);
524
529
  }
525
530
  else {
526
- name = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedNameAfterCallableKeyword(functionTypeText), TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties);
527
- leftParen = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedLeftParenAfterCallableName(functionTypeText), TokenKind_1.TokenKind.LeftParen);
531
+ name = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedNameAfterCallableKeyword(functionKeywordText), TokenKind_1.TokenKind.Identifier, ...TokenKind_1.AllowedProperties);
532
+ leftParen = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedLeftParenAfterCallableName(functionKeywordText), TokenKind_1.TokenKind.LeftParen);
528
533
  //prevent functions from ending with type designators
529
534
  let lastChar = name.text[name.text.length - 1];
530
535
  if (['$', '%', '!', '#', '&'].includes(lastChar)) {
531
536
  //don't throw this error; let the parser continue
532
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionNameCannotEndWithTypeDesignator(functionTypeText, name.text, lastChar)), { range: name.range }));
537
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionNameCannotEndWithTypeDesignator(functionKeywordText, name.text, lastChar)), { range: name.range }));
533
538
  }
534
- //flag functions with keywords for names (only for standard functions)
535
- if (checkIdentifier && TokenKind_1.DisallowedFunctionIdentifiersText.has(name.text.toLowerCase())) {
539
+ //flag functions with keywords for names (only for standard functions - not for class methods)
540
+ if (!options.onlyCallableAsMember && TokenKind_1.DisallowedFunctionIdentifiersText.has(name.text.toLowerCase())) {
536
541
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.cannotUseReservedWordAsIdentifier(name.text)), { range: name.range }));
537
542
  }
538
543
  }
539
544
  let params = [];
540
545
  let asToken;
541
- let typeToken;
546
+ let typeExpr;
542
547
  if (!this.check(TokenKind_1.TokenKind.RightParen)) {
543
548
  do {
544
549
  if (params.length >= Expression_1.CallExpression.MaximumArguments) {
@@ -550,9 +555,9 @@ class Parser {
550
555
  let rightParen = this.advance();
551
556
  if (this.check(TokenKind_1.TokenKind.As)) {
552
557
  asToken = this.advance();
553
- typeToken = this.typeToken();
554
- if (!util_1.util.tokenToBscType(typeToken, this.options.mode === ParseMode.BrighterScript, this.currentNamespaceName)) {
555
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.invalidFunctionReturnType((_a = typeToken.text) !== null && _a !== void 0 ? _a : '')), { range: typeToken.range }));
558
+ typeExpr = this.typeExpression();
559
+ if (!typeExpr.isValidType(this.options.mode)) {
560
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.invalidFunctionReturnType((_a = typeExpr.getText()) !== null && _a !== void 0 ? _a : '')), { range: typeExpr.range }));
556
561
  }
557
562
  }
558
563
  params.reduce((haveFoundOptional, param) => {
@@ -561,17 +566,20 @@ class Parser {
561
566
  }
562
567
  return haveFoundOptional || !!param.defaultValue;
563
568
  }, false);
564
- this.consumeStatementSeparators(true);
569
+ if (options.hasEnd && options.hasBody) {
570
+ // do not go to next statement - we don't care about any other statement
571
+ this.consumeStatementSeparators(true);
572
+ }
565
573
  let func = new Expression_1.FunctionExpression(params, undefined, //body
566
- functionType, undefined, //ending keyword
567
- leftParen, rightParen, asToken, typeToken, //return type
574
+ functionKeyword, undefined, //ending keyword
575
+ leftParen, rightParen, asToken, typeExpr, //return type
568
576
  this.currentFunctionExpression, this.currentNamespaceName, (_c = (_b = this.currentNamespace) === null || _b === void 0 ? void 0 : _b.symbolTable) !== null && _c !== void 0 ? _c : this.symbolTable);
569
577
  //if there is a parent function, register this function with the parent
570
578
  if (this.currentFunctionExpression) {
571
579
  this.currentFunctionExpression.childFunctionExpressions.push(func);
572
580
  }
573
581
  // add the function to the relevant symbol tables
574
- if (!isAnonymous && !forClassMethod) {
582
+ if (!options.onlyCallableAsMember && name) {
575
583
  const funcType = func.getFunctionType();
576
584
  funcType.setName(name.text);
577
585
  // add the function as declared to the current namespace's table
@@ -584,38 +592,35 @@ class Parser {
584
592
  this.currentSymbolTable.addSymbol(fullyQualifiedName, name.range, funcType);
585
593
  }
586
594
  this._references.functionExpressions.push(func);
587
- let previousFunctionExpression = this.currentFunctionExpression;
588
- this.currentFunctionExpression = func;
589
- //make sure to restore the currentFunctionExpression even if the body block fails to parse
590
- try {
591
- //support ending the function with `end sub` OR `end function`
592
- func.body = this.block();
593
- }
594
- finally {
595
- this.currentFunctionExpression = previousFunctionExpression;
596
- }
597
- if (!func.body) {
598
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.callableBlockMissingEndKeyword(functionTypeText)), { range: this.peek().range }));
599
- throw this.lastDiagnosticAsError();
595
+ if (options.hasBody) {
596
+ let previousFunctionExpression = this.currentFunctionExpression;
597
+ this.currentFunctionExpression = func;
598
+ //make sure to restore the currentFunctionExpression even if the body block fails to parse
599
+ try {
600
+ //support ending the function with `end sub` OR `end function`
601
+ func.body = this.block();
602
+ }
603
+ finally {
604
+ this.currentFunctionExpression = previousFunctionExpression;
605
+ }
606
+ if (!func.body) {
607
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.callableBlockMissingEndKeyword(functionKeywordText)), { range: this.peek().range }));
608
+ throw this.lastDiagnosticAsError();
609
+ }
600
610
  }
601
- // consume 'end sub' or 'end function'
602
- func.end = this.advance();
603
- let expectedEndKind = isSub ? TokenKind_1.TokenKind.EndSub : TokenKind_1.TokenKind.EndFunction;
604
- //if `function` is ended with `end sub`, or `sub` is ended with `end function`, then
605
- //add an error but don't hard-fail so the AST can continue more gracefully
606
- if (func.end.kind !== expectedEndKind) {
607
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.mismatchedEndCallableKeyword(functionTypeText, func.end.text)), { range: this.peek().range }));
611
+ if (options.hasEnd) {
612
+ // consume 'end sub' or 'end function'
613
+ func.end = this.advance();
614
+ let expectedEndKind = isSub ? TokenKind_1.TokenKind.EndSub : TokenKind_1.TokenKind.EndFunction;
615
+ //if `function` is ended with `end sub`, or `sub` is ended with `end function`, then
616
+ //add an error but don't hard-fail so the AST can continue more gracefully
617
+ if (func.end.kind !== expectedEndKind) {
618
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.mismatchedEndCallableKeyword(functionKeywordText, func.end.text)), { range: this.peek().range }));
619
+ }
608
620
  }
609
621
  func.callExpressions = this.callExpressions;
610
- if (isAnonymous) {
611
- return func;
612
- }
613
- else {
614
- let result = new Statement_1.FunctionStatement(name, func, this.currentNamespaceName);
615
- func.functionStatement = result;
616
- this._references.functionStatements.push(result);
617
- return result;
618
- }
622
+ func.cacheRange();
623
+ return { name: name, functionExpression: func };
619
624
  }
620
625
  finally {
621
626
  this.namespaceAndFunctionDepth--;
@@ -629,7 +634,7 @@ class Parser {
629
634
  throw this.lastDiagnosticAsError();
630
635
  }
631
636
  const name = this.identifier(...TokenKind_1.AllowedLocalIdentifiers);
632
- let typeToken;
637
+ let typeExpr;
633
638
  let defaultValue;
634
639
  let equalsToken;
635
640
  // parse argument default value
@@ -641,26 +646,26 @@ class Parser {
641
646
  let asToken = null;
642
647
  if (this.check(TokenKind_1.TokenKind.As)) {
643
648
  asToken = this.advance();
644
- typeToken = this.typeToken();
645
- if (!util_1.util.tokenToBscType(typeToken, this.options.mode === ParseMode.BrighterScript, this.currentNamespaceName)) {
646
- this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionParameterTypeIsInvalid(name.text, typeToken.text)), { range: typeToken.range }));
649
+ typeExpr = this.typeExpression();
650
+ if (!typeExpr.isValidType(this.options.mode)) {
651
+ this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.functionParameterTypeIsInvalid(name.text, typeExpr.getText())), { range: typeExpr.range }));
647
652
  throw this.lastDiagnosticAsError();
648
653
  }
649
654
  }
650
- let type;
651
- if (typeToken) {
652
- type = util_1.util.tokenToBscType(typeToken, true, this.currentNamespaceName);
655
+ let typeInContext;
656
+ if (typeExpr) {
657
+ typeInContext = typeExpr.type;
653
658
  }
654
659
  else if (defaultValue) {
655
- type = getBscTypeFromExpression(defaultValue, this.currentFunctionExpression);
656
- if ((0, reflection_1.isInvalidType)(type)) {
657
- type = new DynamicType_1.DynamicType();
660
+ typeInContext = getBscTypeFromExpression(defaultValue, this.currentFunctionExpression);
661
+ if ((0, reflection_1.isInvalidType)(typeInContext)) {
662
+ typeInContext = new DynamicType_1.DynamicType();
658
663
  }
659
664
  }
660
665
  else {
661
- type = new DynamicType_1.DynamicType();
666
+ typeInContext = new DynamicType_1.DynamicType();
662
667
  }
663
- return new Expression_1.FunctionParameterExpression(name, type, equalsToken, defaultValue, asToken, typeToken, this.currentNamespaceName);
668
+ return new Expression_1.FunctionParameterExpression(name, typeInContext, equalsToken, defaultValue, asToken, typeExpr, this.currentNamespaceName);
664
669
  }
665
670
  assignment() {
666
671
  let name = this.identifier(...this.allowedLocalIdentifiers);
@@ -854,6 +859,12 @@ class Parser {
854
859
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.expectedExpressionAfterForEachIn()), { range: this.peek().range }));
855
860
  throw this.lastDiagnosticAsError();
856
861
  }
862
+ let itemType = new DynamicType_1.DynamicType();
863
+ const targetType = getBscTypeFromExpression(target, this.currentFunctionExpression);
864
+ if ((0, reflection_1.isArrayType)(targetType)) {
865
+ itemType = targetType.getDefaultType();
866
+ }
867
+ this.currentSymbolTable.addSymbol(name.text, name.range, itemType);
857
868
  this.consumeStatementSeparators();
858
869
  let body = this.block(TokenKind_1.TokenKind.EndFor, TokenKind_1.TokenKind.Next);
859
870
  if (!body) {
@@ -861,12 +872,6 @@ class Parser {
861
872
  throw this.lastDiagnosticAsError();
862
873
  }
863
874
  let endFor = this.advance();
864
- let itemType = new DynamicType_1.DynamicType();
865
- const targetType = getBscTypeFromExpression(target, this.currentFunctionExpression);
866
- if ((0, reflection_1.isArrayType)(targetType)) {
867
- itemType = targetType.getDefaultType();
868
- }
869
- this.currentSymbolTable.addSymbol(name.text, name.range, itemType);
870
875
  return new Statement_1.ForEachStatement(forEach, name, maybeIn, target, body, endFor);
871
876
  }
872
877
  exitFor() {
@@ -917,6 +922,8 @@ class Parser {
917
922
  result.body = body;
918
923
  result.endKeyword = endKeyword;
919
924
  this._references.namespaceStatements.push(result);
925
+ //cache the range property so that plugins can't affect it
926
+ result.cacheRange();
920
927
  return result;
921
928
  }
922
929
  /**
@@ -999,6 +1006,8 @@ class Parser {
999
1006
  let leftParen = this.advance();
1000
1007
  annotation.call = this.finishCall(leftParen, annotation, false);
1001
1008
  }
1009
+ //cache the range property so that plugins can't affect it
1010
+ annotation.cacheRange();
1002
1011
  return annotation;
1003
1012
  }
1004
1013
  ternaryExpression(test) {
@@ -1107,7 +1116,7 @@ class Parser {
1107
1116
  }
1108
1117
  tryCatchStatement() {
1109
1118
  const tryToken = this.advance();
1110
- const statement = new Statement_1.TryCatchStatement(tryToken);
1119
+ const statement = new Statement_1.TryCatchStatement({ try: tryToken });
1111
1120
  //ensure statement separator
1112
1121
  this.consumeStatementSeparators();
1113
1122
  statement.tryBranch = this.block(TokenKind_1.TokenKind.Catch, TokenKind_1.TokenKind.EndTry);
@@ -1116,27 +1125,26 @@ class Parser {
1116
1125
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.expectedCatchBlockInTryCatch()), { range: this.peek().range }));
1117
1126
  //gracefully handle end-try
1118
1127
  if (peek.kind === TokenKind_1.TokenKind.EndTry) {
1119
- statement.endTryToken = this.advance();
1128
+ statement.tokens.endTry = this.advance();
1120
1129
  }
1121
1130
  return statement;
1122
1131
  }
1123
- else {
1124
- statement.catchToken = this.advance();
1125
- }
1132
+ const catchStmt = new Statement_1.CatchStatement({ catch: this.advance() });
1133
+ statement.catchStatement = catchStmt;
1126
1134
  const exceptionVarToken = this.tryConsume(DiagnosticMessages_1.DiagnosticMessages.missingExceptionVarToFollowCatch(), TokenKind_1.TokenKind.Identifier, ...this.allowedLocalIdentifiers);
1127
1135
  if (exceptionVarToken) {
1128
1136
  // force it into an identifier so the AST makes some sense
1129
1137
  exceptionVarToken.kind = TokenKind_1.TokenKind.Identifier;
1130
- statement.exceptionVariable = exceptionVarToken;
1138
+ catchStmt.exceptionVariable = exceptionVarToken;
1131
1139
  }
1132
1140
  //ensure statement sepatator
1133
1141
  this.consumeStatementSeparators();
1134
- statement.catchBranch = this.block(TokenKind_1.TokenKind.EndTry);
1142
+ catchStmt.catchBranch = this.block(TokenKind_1.TokenKind.EndTry);
1135
1143
  if (this.peek().kind !== TokenKind_1.TokenKind.EndTry) {
1136
1144
  this.diagnostics.push(Object.assign(Object.assign({}, DiagnosticMessages_1.DiagnosticMessages.expectedEndTryToTerminateTryCatch()), { range: this.peek().range }));
1137
1145
  }
1138
1146
  else {
1139
- statement.endTryToken = this.advance();
1147
+ statement.tokens.endTry = this.advance();
1140
1148
  }
1141
1149
  return statement;
1142
1150
  }
@@ -1403,12 +1411,10 @@ class Parser {
1403
1411
  if ((0, reflection_1.isIndexedGetExpression)(left)) {
1404
1412
  return new Statement_1.IndexedSetStatement(left.obj, left.index, operator.kind === TokenKind_1.TokenKind.Equal
1405
1413
  ? right
1406
- : new Expression_1.BinaryExpression(left, operator, right), left.openingSquare, left.closingSquare);
1414
+ : new Expression_1.BinaryExpression(left, operator, right), left.openingSquare, left.closingSquare, operator);
1407
1415
  }
1408
1416
  else if ((0, reflection_1.isDottedGetExpression)(left)) {
1409
- const dottedSetStmt = new Statement_1.DottedSetStatement(left.obj, left.name, operator.kind === TokenKind_1.TokenKind.Equal
1410
- ? right
1411
- : new Expression_1.BinaryExpression(left, operator, right));
1417
+ const dottedSetStmt = new Statement_1.DottedSetStatement(left.obj, left.name, operator.kind === TokenKind_1.TokenKind.Equal ? right : new Expression_1.BinaryExpression(left, operator, right), left.dot, operator);
1412
1418
  this._references.dottedSetStatements.push(dottedSetStmt);
1413
1419
  return dottedSetStmt;
1414
1420
  }
@@ -1584,7 +1590,7 @@ class Parser {
1584
1590
  }
1585
1591
  anonymousFunction() {
1586
1592
  if (this.checkAny(TokenKind_1.TokenKind.Sub, TokenKind_1.TokenKind.Function)) {
1587
- const func = this.functionDeclaration(true);
1593
+ const func = this.functionDeclaration({ hasName: false, hasBody: true, hasEnd: true }).functionExpression;
1588
1594
  //if there's an open paren after this, this is an IIFE
1589
1595
  if (this.check(TokenKind_1.TokenKind.LeftParen)) {
1590
1596
  return this.finishCall(this.advance(), func);
@@ -1762,9 +1768,6 @@ class Parser {
1762
1768
  }
1763
1769
  while (this.match(TokenKind_1.TokenKind.Newline)) { }
1764
1770
  const closingParen = this.consume(DiagnosticMessages_1.DiagnosticMessages.expectedRightParenAfterFunctionCallArguments(), TokenKind_1.TokenKind.RightParen);
1765
- if ((0, reflection_1.isVariableExpression)(callee)) {
1766
- callee.isCalled = true;
1767
- }
1768
1771
  let expression = new Expression_1.CallExpression(callee, openingParen, closingParen, args, this.currentNamespaceName);
1769
1772
  if (addToCallExpressionList) {
1770
1773
  this.callExpressions.push(expression);
@@ -1776,7 +1779,7 @@ class Parser {
1776
1779
  * Allows for built-in types (double, string, etc.) or namespaced custom types in Brighterscript mode
1777
1780
  * Will return a token of whatever is next to be parsed (unless `advanceIfUnknown` is false, in which case undefined will be returned instead
1778
1781
  */
1779
- typeToken() {
1782
+ typeExpression() {
1780
1783
  let typeToken;
1781
1784
  if (this.checkAny(...TokenKind_1.DeclarableTypes)) {
1782
1785
  // Token is a built in type
@@ -1797,18 +1800,23 @@ class Parser {
1797
1800
  // just get whatever's next
1798
1801
  typeToken = this.advance();
1799
1802
  }
1800
- if (typeToken && this.options.mode === ParseMode.BrighterScript) {
1803
+ //TODO: to support InterfaceTypeLiterals - (eg. `{name as string; age as integer}`), check if "typeToken" is a curly bracket, and do something else
1804
+ let typeExpr = new Expression_1.TypeExpression({ type: typeToken }, this.currentNamespaceName);
1805
+ if (this.options.mode === ParseMode.BrighterScript) {
1801
1806
  // Check if it is an array - that is, if it has `[]` after the type
1802
- // eg. `string[]` or `SomeKlass[]`
1803
- if (this.check(TokenKind_1.TokenKind.LeftSquareBracket)) {
1804
- this.advance();
1807
+ // eg. `string[]` or `SomeKlass[]` or `float[][][]`
1808
+ while (this.check(TokenKind_1.TokenKind.LeftSquareBracket)) {
1809
+ const leftBracket = this.advance();
1805
1810
  if (this.check(TokenKind_1.TokenKind.RightSquareBracket)) {
1806
1811
  const rightBracket = this.advance();
1807
- typeToken = (0, creators_1.createToken)(TokenKind_1.TokenKind.Identifier, typeToken.text + '[]', util_1.util.getRange(typeToken, rightBracket));
1812
+ typeExpr = new Expression_1.ArrayTypeExpression([typeExpr], { leftBracket: leftBracket, rightBracket: rightBracket }, this.currentNamespaceName);
1813
+ }
1814
+ else {
1815
+ break;
1808
1816
  }
1809
1817
  }
1810
1818
  }
1811
- return typeToken;
1819
+ return typeExpr;
1812
1820
  }
1813
1821
  primary() {
1814
1822
  switch (true) {
@@ -2389,6 +2397,9 @@ class Parser {
2389
2397
  this._references.expressions.add(s.initialValue);
2390
2398
  }
2391
2399
  },
2400
+ InterfaceStatement: s => {
2401
+ this._references.interfaceStatements.push(s);
2402
+ },
2392
2403
  NamespaceStatement: s => {
2393
2404
  this._references.namespaceStatements.push(s);
2394
2405
  },
@@ -2402,7 +2413,7 @@ class Parser {
2402
2413
  this._references.libraryStatements.push(s);
2403
2414
  },
2404
2415
  FunctionExpression: (expression, parent) => {
2405
- if (!(0, reflection_1.isClassMethodStatement)(parent)) {
2416
+ if (!(0, reflection_1.isClassMethodStatement)(parent) && !(0, reflection_1.isInterfaceMethodStatement)(parent)) {
2406
2417
  this._references.functionExpressions.push(expression);
2407
2418
  }
2408
2419
  },
@@ -2534,7 +2545,7 @@ class References {
2534
2545
  if (!this._interfaceStatementLookup) {
2535
2546
  this._interfaceStatementLookup = new Map();
2536
2547
  for (const stmt of this.interfaceStatements) {
2537
- this._interfaceStatementLookup.set(stmt.fullName.toLowerCase(), stmt);
2548
+ this._interfaceStatementLookup.set(stmt.getName(ParseMode.BrighterScript).toLowerCase(), stmt);
2538
2549
  }
2539
2550
  }
2540
2551
  return this._interfaceStatementLookup;
@@ -2579,7 +2590,7 @@ function getBscTypeFromExpression(expression, functionExpression) {
2579
2590
  //Associative array literal
2580
2591
  }
2581
2592
  else if ((0, reflection_1.isAALiteralExpression)(expression)) {
2582
- return new ObjectType_1.ObjectType(expression.memberTable);
2593
+ return new ObjectType_1.ObjectType('object', expression.memberTable);
2583
2594
  //Array literal
2584
2595
  }
2585
2596
  else if ((0, reflection_1.isArrayLiteralExpression)(expression)) {
@@ -2590,7 +2601,7 @@ function getBscTypeFromExpression(expression, functionExpression) {
2590
2601
  //function call
2591
2602
  }
2592
2603
  else if ((0, reflection_1.isNewExpression)(expression)) {
2593
- return (0, helpers_1.getTypeFromNewExpression)(expression, functionExpression); // new CustomType(expression.className.getName(ParseMode.BrighterScript));
2604
+ return (0, helpers_1.getTypeFromNewExpression)(expression, functionExpression);
2594
2605
  //Function call
2595
2606
  }
2596
2607
  else if ((0, reflection_1.isCallExpression)(expression)) {