@@ -204,8 +204,6 @@ namespace ts {
204204 const evolvingArrayTypes: EvolvingArrayType[] = [];
205205
206206 const unknownSymbol = createSymbol(SymbolFlags.Property, "unknown");
207- const untypedModuleSymbol = createSymbol(SymbolFlags.ValueModule, "<untyped>");
208- untypedModuleSymbol.exports = createMap<Symbol>();
209207 const resolvingSymbol = createSymbol(0, "__resolving__");
210208
211209 const anyType = createIntrinsicType(TypeFlags.Any, "any");
@@ -1267,7 +1265,7 @@ namespace ts {
12671265
12681266 if (moduleSymbol) {
12691267 let exportDefaultSymbol: Symbol;
1270- if (isUntypedOrShorthandAmbientModuleSymbol (moduleSymbol)) {
1268+ if (isShorthandAmbientModuleSymbol (moduleSymbol)) {
12711269 exportDefaultSymbol = moduleSymbol;
12721270 }
12731271 else {
@@ -1347,7 +1345,7 @@ namespace ts {
13471345 if (targetSymbol) {
13481346 const name = specifier.propertyName || specifier.name;
13491347 if (name.text) {
1350- if (isUntypedOrShorthandAmbientModuleSymbol (moduleSymbol)) {
1348+ if (isShorthandAmbientModuleSymbol (moduleSymbol)) {
13511349 return moduleSymbol;
13521350 }
13531351
@@ -1623,19 +1621,15 @@ namespace ts {
16231621 if (isForAugmentation) {
16241622 const diag = Diagnostics.Invalid_module_name_in_augmentation_Module_0_resolves_to_an_untyped_module_at_1_which_cannot_be_augmented;
16251623 error(errorNode, diag, moduleReference, resolvedModule.resolvedFileName);
1626- return undefined;
16271624 }
16281625 else if (noImplicitAny && moduleNotFoundError) {
16291626 error(errorNode,
16301627 Diagnostics.Could_not_find_a_declaration_file_for_module_0_1_implicitly_has_an_any_type,
16311628 moduleReference,
16321629 resolvedModule.resolvedFileName);
1633- return undefined;
16341630 }
1635- // Unlike a failed import, an untyped module produces a dummy symbol.
1636- // This is checked for by `isUntypedOrShorthandAmbientModuleSymbol`.
1637- // This must be different than `unknownSymbol` because `getBaseConstructorTypeOfClass` won't fail for `unknownSymbol`.
1638- return untypedModuleSymbol;
1631+ // Failed imports and untyped modules are both treated in an untyped manner; only difference is whether we give a diagnostic first.
1632+ return undefined;
16391633 }
16401634
16411635 if (moduleNotFoundError) {
@@ -4405,7 +4399,7 @@ namespace ts {
44054399 function getTypeOfFuncClassEnumModule(symbol: Symbol): Type {
44064400 const links = getSymbolLinks(symbol);
44074401 if (!links.type) {
4408- if (symbol.flags & SymbolFlags.Module && isUntypedOrShorthandAmbientModuleSymbol (symbol)) {
4402+ if (symbol.flags & SymbolFlags.Module && isShorthandAmbientModuleSymbol (symbol)) {
44094403 links.type = anyType;
44104404 }
44114405 else {
@@ -4641,7 +4635,8 @@ namespace ts {
46414635 * The base constructor of a class can resolve to
46424636 * * undefinedType if the class has no extends clause,
46434637 * * unknownType if an error occurred during resolution of the extends expression,
4644- * * nullType if the extends expression is the null value, or
4638+ * * nullType if the extends expression is the null value,
4639+ * * anyType if the extends expression has type any, or
46454640 * * an object type with at least one construct signature.
46464641 */
46474642 function getBaseConstructorTypeOfClass(type: InterfaceType): Type {
@@ -4663,7 +4658,7 @@ namespace ts {
46634658 error(type.symbol.valueDeclaration, Diagnostics._0_is_referenced_directly_or_indirectly_in_its_own_base_expression, symbolToString(type.symbol));
46644659 return type.resolvedBaseConstructorType = unknownType;
46654660 }
4666- if (baseConstructorType !== unknownType && baseConstructorType !== nullWideningType && !isConstructorType(baseConstructorType)) {
4661+ if (!( baseConstructorType.flags & TypeFlags.Any) && baseConstructorType !== nullWideningType && !isConstructorType(baseConstructorType)) {
46674662 error(baseTypeNode.expression, Diagnostics.Type_0_is_not_a_constructor_function_type, typeToString(baseConstructorType));
46684663 return type.resolvedBaseConstructorType = unknownType;
46694664 }
@@ -4695,7 +4690,7 @@ namespace ts {
46954690 function resolveBaseTypesOfClass(type: InterfaceType): void {
46964691 type.resolvedBaseTypes = type.resolvedBaseTypes || emptyArray;
46974692 const baseConstructorType = getApparentType(getBaseConstructorTypeOfClass(type));
4698- if (!(baseConstructorType.flags & (TypeFlags.Object | TypeFlags.Intersection))) {
4693+ if (!(baseConstructorType.flags & (TypeFlags.Object | TypeFlags.Intersection | TypeFlags.Any ))) {
46994694 return;
47004695 }
47014696 const baseTypeNode = getBaseTypeNodeOfClass(type);
@@ -4708,6 +4703,9 @@ namespace ts {
47084703 // type arguments in the same manner as a type reference to get the same error reporting experience.
47094704 baseType = getTypeFromClassOrInterfaceReference(baseTypeNode, baseConstructorType.symbol);
47104705 }
4706+ else if (baseConstructorType.flags & TypeFlags.Any) {
4707+ baseType = baseConstructorType;
4708+ }
47114709 else {
47124710 // The class derives from a "class-like" constructor function, check that we have at least one construct signature
47134711 // with a matching number of type parameters and use the return type of the first instantiated signature. Elsewhere
@@ -4761,10 +4759,10 @@ namespace ts {
47614759 return true;
47624760 }
47634761
4764- // A valid base type is any non-generic object type or intersection of non-generic
4762+ // A valid base type is `any`, any non-generic object type or intersection of non-generic
47654763 // object types.
47664764 function isValidBaseType(type: Type): boolean {
4767- return type.flags & (TypeFlags.Object | TypeFlags.NonPrimitive) && !isGenericMappedType(type) ||
4765+ return type.flags & (TypeFlags.Object | TypeFlags.NonPrimitive | TypeFlags.Any ) && !isGenericMappedType(type) ||
47684766 type.flags & TypeFlags.Intersection && !forEach((<IntersectionType>type).types, t => !isValidBaseType(t));
47694767 }
47704768
@@ -5176,7 +5174,11 @@ namespace ts {
51765174 addInheritedMembers(members, getPropertiesOfType(instantiatedBaseType));
51775175 callSignatures = concatenate(callSignatures, getSignaturesOfType(instantiatedBaseType, SignatureKind.Call));
51785176 constructSignatures = concatenate(constructSignatures, getSignaturesOfType(instantiatedBaseType, SignatureKind.Construct));
5179- stringIndexInfo = stringIndexInfo || getIndexInfoOfType(instantiatedBaseType, IndexKind.String);
5177+ if (!stringIndexInfo) {
5178+ stringIndexInfo = instantiatedBaseType === anyType ?
5179+ createIndexInfo(anyType, /*isReadonly*/ false) :
5180+ getIndexInfoOfType(instantiatedBaseType, IndexKind.String);
5181+ }
51805182 numberIndexInfo = numberIndexInfo || getIndexInfoOfType(instantiatedBaseType, IndexKind.Number);
51815183 }
51825184 }
@@ -5418,6 +5420,7 @@ namespace ts {
54185420 // Combinations of function, class, enum and module
54195421 let members = emptySymbols;
54205422 let constructSignatures: Signature[] = emptyArray;
5423+ let stringIndexInfo: IndexInfo = undefined;
54215424 if (symbol.exports) {
54225425 members = getExportsOfSymbol(symbol);
54235426 }
@@ -5432,9 +5435,12 @@ namespace ts {
54325435 members = createSymbolTable(getNamedMembers(members));
54335436 addInheritedMembers(members, getPropertiesOfType(baseConstructorType));
54345437 }
5438+ else if (baseConstructorType === anyType) {
5439+ stringIndexInfo = createIndexInfo(anyType, /*isReadonly*/ false);
5440+ }
54355441 }
54365442 const numberIndexInfo = symbol.flags & SymbolFlags.Enum ? enumNumberIndexInfo : undefined;
5437- setStructuredTypeMembers(type, members, emptyArray, constructSignatures, undefined , numberIndexInfo);
5443+ setStructuredTypeMembers(type, members, emptyArray, constructSignatures, stringIndexInfo , numberIndexInfo);
54385444 // We resolve the members before computing the signatures because a signature may use
54395445 // typeof with a qualified name expression that circularly references the type we are
54405446 // in the process of resolving (see issue #6072). The temporarily empty signature list
@@ -22172,7 +22178,7 @@ namespace ts {
2217222178
2217322179 function moduleExportsSomeValue(moduleReferenceExpression: Expression): boolean {
2217422180 let moduleSymbol = resolveExternalModuleName(moduleReferenceExpression.parent, moduleReferenceExpression);
22175- if (!moduleSymbol || isUntypedOrShorthandAmbientModuleSymbol (moduleSymbol)) {
22181+ if (!moduleSymbol || isShorthandAmbientModuleSymbol (moduleSymbol)) {
2217622182 // If the module is not found or is shorthand, assume that it may export a value.
2217722183 return true;
2217822184 }
0 commit comments