@zzzen/pyright-internal 1.2.0-dev.20220724 → 1.2.0-dev.20220731

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 (58) hide show
  1. package/dist/analyzer/checker.js +11 -3
  2. package/dist/analyzer/checker.js.map +1 -1
  3. package/dist/analyzer/constraintSolver.js +4 -1
  4. package/dist/analyzer/constraintSolver.js.map +1 -1
  5. package/dist/analyzer/enums.d.ts +13 -0
  6. package/dist/analyzer/enums.js +207 -0
  7. package/dist/analyzer/enums.js.map +1 -0
  8. package/dist/analyzer/importStatementUtils.d.ts +2 -0
  9. package/dist/analyzer/importStatementUtils.js +49 -1
  10. package/dist/analyzer/importStatementUtils.js.map +1 -1
  11. package/dist/analyzer/parseTreeUtils.js +5 -0
  12. package/dist/analyzer/parseTreeUtils.js.map +1 -1
  13. package/dist/analyzer/patternMatching.js +2 -2
  14. package/dist/analyzer/patternMatching.js.map +1 -1
  15. package/dist/analyzer/properties.js +1 -1
  16. package/dist/analyzer/properties.js.map +1 -1
  17. package/dist/analyzer/typeEvaluator.js +158 -219
  18. package/dist/analyzer/typeEvaluator.js.map +1 -1
  19. package/dist/analyzer/typeEvaluatorTypes.d.ts +3 -1
  20. package/dist/analyzer/typeEvaluatorTypes.js.map +1 -1
  21. package/dist/analyzer/typeEvaluatorWithTracker.js +1 -0
  22. package/dist/analyzer/typeEvaluatorWithTracker.js.map +1 -1
  23. package/dist/analyzer/typeGuards.js +1 -1
  24. package/dist/analyzer/typeGuards.js.map +1 -1
  25. package/dist/analyzer/typePrinter.js +7 -1
  26. package/dist/analyzer/typePrinter.js.map +1 -1
  27. package/dist/analyzer/typeUtils.d.ts +0 -1
  28. package/dist/analyzer/typeUtils.js +2 -17
  29. package/dist/analyzer/typeUtils.js.map +1 -1
  30. package/dist/analyzer/types.js +10 -1
  31. package/dist/analyzer/types.js.map +1 -1
  32. package/dist/commands/commandResult.js +1 -1
  33. package/dist/commands/commandResult.js.map +1 -1
  34. package/dist/common/workspaceEditUtils.d.ts +1 -0
  35. package/dist/common/workspaceEditUtils.js +10 -6
  36. package/dist/common/workspaceEditUtils.js.map +1 -1
  37. package/dist/languageServerBase.d.ts +2 -1
  38. package/dist/languageServerBase.js +2 -1
  39. package/dist/languageServerBase.js.map +1 -1
  40. package/dist/languageService/completionProvider.js +0 -1
  41. package/dist/languageService/completionProvider.js.map +1 -1
  42. package/dist/tests/fourslash/completions.commitChars.fourslash.js +12 -0
  43. package/dist/tests/fourslash/completions.commitChars.fourslash.js.map +1 -1
  44. package/dist/tests/fourslash/hover.init.fourslash.js +2 -2
  45. package/dist/tests/fourslash/hover.init.fourslash.js.map +1 -1
  46. package/dist/tests/harness/fourslash/fourSlashParser.js +5 -1
  47. package/dist/tests/harness/fourslash/fourSlashParser.js.map +1 -1
  48. package/dist/tests/harness/fourslash/testState.js +6 -6
  49. package/dist/tests/harness/fourslash/testState.js.map +1 -1
  50. package/dist/tests/testState.test.js +1 -1
  51. package/dist/tests/testState.test.js.map +1 -1
  52. package/dist/tests/typeEvaluator1.test.js +5 -1
  53. package/dist/tests/typeEvaluator1.test.js.map +1 -1
  54. package/dist/tests/typeEvaluator3.test.js +8 -0
  55. package/dist/tests/typeEvaluator3.test.js.map +1 -1
  56. package/dist/workspaceMap.js +1 -1
  57. package/dist/workspaceMap.js.map +1 -1
  58. package/package.json +2 -2
@@ -55,6 +55,7 @@ const constraintSolver_1 = require("./constraintSolver");
55
55
  const constructorTransform_1 = require("./constructorTransform");
56
56
  const dataClasses_1 = require("./dataClasses");
57
57
  const declarationUtils_1 = require("./declarationUtils");
58
+ const enums_1 = require("./enums");
58
59
  const functionTransform_1 = require("./functionTransform");
59
60
  const namedTuples_1 = require("./namedTuples");
60
61
  const ParseTreeUtils = __importStar(require("./parseTreeUtils"));
@@ -798,23 +799,46 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
798
799
  }
799
800
  else {
800
801
  // Evaluate the format string expressions in this context.
801
- node.strings.forEach((str) => {
802
- if (str.nodeType === 27 /* FormatString */) {
803
- str.expressions.forEach((expr) => {
804
- getTypeOfExpression(expr);
805
- });
802
+ let isLiteralString = true;
803
+ let isIncomplete = false;
804
+ node.strings.forEach((expr) => {
805
+ const typeResult = getTypeOfString(expr);
806
+ if (typeResult.isIncomplete) {
807
+ isIncomplete = true;
808
+ }
809
+ let isExprLiteralString = false;
810
+ if ((0, types_1.isClassInstance)(typeResult.type)) {
811
+ if (types_1.ClassType.isBuiltIn(typeResult.type, 'str') && typeResult.type.literalValue !== undefined) {
812
+ isExprLiteralString = true;
813
+ }
814
+ else if (types_1.ClassType.isBuiltIn(typeResult === null || typeResult === void 0 ? void 0 : typeResult.type, 'LiteralString')) {
815
+ isExprLiteralString = true;
816
+ }
817
+ }
818
+ if (!isExprLiteralString) {
819
+ isLiteralString = false;
806
820
  }
807
821
  });
808
822
  const isBytes = (node.strings[0].token.flags & 32 /* Bytes */) !== 0;
809
823
  // Don't create a literal type if it's an f-string.
810
824
  if (node.strings.some((str) => str.nodeType === 27 /* FormatString */)) {
811
- typeResult = {
812
- type: getBuiltInObject(node, isBytes ? 'bytes' : 'str'),
813
- };
825
+ if (isLiteralString) {
826
+ const literalStringType = getTypingType(node, 'LiteralString');
827
+ if (literalStringType && (0, types_1.isInstantiableClass)(literalStringType)) {
828
+ typeResult = { type: types_1.ClassType.cloneAsInstance(literalStringType) };
829
+ }
830
+ }
831
+ if (!typeResult) {
832
+ typeResult = {
833
+ type: getBuiltInObject(node, isBytes ? 'bytes' : 'str'),
834
+ isIncomplete,
835
+ };
836
+ }
814
837
  }
815
838
  else {
816
839
  typeResult = {
817
840
  type: cloneBuiltinObjectWithLiteral(node, isBytes ? 'bytes' : 'str', node.strings.map((s) => s.value).join('')),
841
+ isIncomplete,
818
842
  };
819
843
  }
820
844
  }
@@ -825,9 +849,34 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
825
849
  let typeResult;
826
850
  // Don't create a literal type if it's an f-string.
827
851
  if (node.nodeType === 27 /* FormatString */) {
828
- typeResult = {
829
- type: getBuiltInObject(node, isBytes ? 'bytes' : 'str'),
830
- };
852
+ let isLiteralString = true;
853
+ // If all of the format expressions are of type LiteralString, then
854
+ // the resulting formatted string is also LiteralString.
855
+ node.expressions.forEach((expr) => {
856
+ const exprType = getTypeOfExpression(expr).type;
857
+ if (!(0, types_1.isClassInstance)(exprType)) {
858
+ isLiteralString = false;
859
+ return;
860
+ }
861
+ if (types_1.ClassType.isBuiltIn(exprType, 'LiteralString')) {
862
+ return;
863
+ }
864
+ if (types_1.ClassType.isBuiltIn(exprType, 'str') && exprType.literalValue !== undefined) {
865
+ return;
866
+ }
867
+ isLiteralString = false;
868
+ });
869
+ if (!isBytes && isLiteralString) {
870
+ const literalStringType = getTypingType(node, 'LiteralString');
871
+ if (literalStringType && (0, types_1.isInstantiableClass)(literalStringType)) {
872
+ typeResult = { type: types_1.ClassType.cloneAsInstance(literalStringType) };
873
+ }
874
+ }
875
+ if (!typeResult) {
876
+ typeResult = {
877
+ type: getBuiltInObject(node, isBytes ? 'bytes' : 'str'),
878
+ };
879
+ }
831
880
  }
832
881
  else {
833
882
  typeResult = {
@@ -836,6 +885,26 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
836
885
  }
837
886
  return typeResult;
838
887
  }
888
+ function stripLiteralValue(type) {
889
+ if ((0, types_1.isClass)(type)) {
890
+ if (type.literalValue !== undefined) {
891
+ type = types_1.ClassType.cloneWithLiteral(type, /* value */ undefined);
892
+ }
893
+ else if (types_1.ClassType.isBuiltIn(type, 'LiteralString')) {
894
+ // Handle "LiteralString" specially.
895
+ if (strClassType && (0, types_1.isInstantiableClass)(strClassType)) {
896
+ type = types_1.ClassType.cloneAsInstance(strClassType);
897
+ }
898
+ }
899
+ return type;
900
+ }
901
+ if ((0, types_1.isUnion)(type)) {
902
+ return (0, typeUtils_1.mapSubtypes)(type, (subtype) => {
903
+ return stripLiteralValue(subtype);
904
+ });
905
+ }
906
+ return type;
907
+ }
839
908
  function getTypeOfParameterAnnotation(paramTypeNode, paramCategory) {
840
909
  return getTypeOfAnnotation(paramTypeNode, {
841
910
  associateTypeVarsWithScope: true,
@@ -1164,6 +1233,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
1164
1233
  if (memberInfo) {
1165
1234
  return {
1166
1235
  type: memberInfo.type,
1236
+ classType: memberInfo.classType,
1167
1237
  isIncomplete: !!memberInfo.isTypeIncomplete,
1168
1238
  isAsymmetricDescriptor: memberInfo.isAsymmetricDescriptor,
1169
1239
  };
@@ -1903,7 +1973,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
1903
1973
  if (types_1.TypeBase.isInstance(destType) &&
1904
1974
  !(0, symbolNameUtils_1.isConstantName)(nameValue) &&
1905
1975
  !(0, symbolUtils_1.isFinalVariable)(symbolWithScope.symbol)) {
1906
- destType = (0, typeUtils_1.stripLiteralValue)(destType);
1976
+ destType = stripLiteralValue(destType);
1907
1977
  }
1908
1978
  }
1909
1979
  }
@@ -2090,7 +2160,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
2090
2160
  const removedEntries = sourceEntryTypes.splice(targetUnpackIndex, sourceEntryTypes.length - targetTypes.length + 1);
2091
2161
  let combinedTypes = (0, types_1.combineTypes)(removedEntries);
2092
2162
  if (target.nodeType === 31 /* List */) {
2093
- combinedTypes = (0, typeUtils_1.stripLiteralValue)(combinedTypes);
2163
+ combinedTypes = stripLiteralValue(combinedTypes);
2094
2164
  }
2095
2165
  sourceEntryTypes.splice(targetUnpackIndex, 0, combinedTypes);
2096
2166
  }
@@ -3176,22 +3246,9 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
3176
3246
  baseType = types_1.ClassType.cloneAsInstance(strClassType);
3177
3247
  }
3178
3248
  // Handle the special case of 'name' and 'value' members within an enum.
3179
- if (types_1.ClassType.isEnumClass(baseType)) {
3180
- const literalValue = baseType.literalValue;
3181
- if (literalValue instanceof types_1.EnumLiteral) {
3182
- if (memberName === 'name' || memberName === '_name_') {
3183
- const strClass = getBuiltInType(node, 'str');
3184
- if ((0, types_1.isInstantiableClass)(strClass)) {
3185
- return {
3186
- type: types_1.ClassType.cloneAsInstance(types_1.ClassType.cloneWithLiteral(strClass, literalValue.itemName)),
3187
- isIncomplete,
3188
- };
3189
- }
3190
- }
3191
- else if (memberName === 'value' || memberName === '_value_') {
3192
- return { type: literalValue.itemType, isIncomplete };
3193
- }
3194
- }
3249
+ const enumMemberResult = (0, enums_1.getTypeOfEnumMember)(evaluatorInterface, node, baseType, memberName, isIncomplete);
3250
+ if (enumMemberResult) {
3251
+ return enumMemberResult;
3195
3252
  }
3196
3253
  const typeResult = getTypeOfObjectMember(node.memberName, baseType, memberName, usage, diag,
3197
3254
  /* memberAccessFlags */ undefined, baseTypeResult.bindToType);
@@ -3451,7 +3508,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
3451
3508
  // because that case is used for super() calls where we want
3452
3509
  // to leave the Self type generic (not specialized).
3453
3510
  const selfClass = bindToType ? undefined : classType;
3454
- const typeResult = getTypeOfMemberInternal(errorNode, memberInfo, selfClass);
3511
+ const typeResult = getTypeOfMemberInternal(memberInfo, selfClass);
3455
3512
  if (typeResult) {
3456
3513
  type = typeResult.type;
3457
3514
  if (typeResult.isIncomplete) {
@@ -5853,7 +5910,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
5853
5910
  if ((0, types_1.isClassInstance)(subtype) ||
5854
5911
  ((0, types_1.isTypeVar)(subtype) && types_1.TypeBase.isInstance(subtype)) ||
5855
5912
  (0, types_1.isNoneInstance)(subtype)) {
5856
- return (0, typeUtils_1.convertToInstantiable)((0, typeUtils_1.stripLiteralValue)(subtype));
5913
+ return (0, typeUtils_1.convertToInstantiable)(stripLiteralValue(subtype));
5857
5914
  }
5858
5915
  return types_1.AnyType.create();
5859
5916
  });
@@ -5892,18 +5949,14 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
5892
5949
  addDiagnostic(fileInfo.diagnosticRuleSet.reportGeneralTypeIssues, diagnosticRules_1.DiagnosticRule.reportGeneralTypeIssues, localize_1.Localizer.Diagnostic.typeNotIntantiable().format({ type: className }), errorNode);
5893
5950
  return types_1.AnyType.create();
5894
5951
  }
5895
- if (className === 'Enum' ||
5896
- className === 'IntEnum' ||
5897
- className === 'StrEnum' ||
5898
- className === 'Flag' ||
5899
- className === 'IntFlag') {
5900
- return createEnumType(errorNode, expandedSubtype, argList);
5952
+ if ((0, enums_1.isKnownEnumType)(className)) {
5953
+ return (0, enums_1.createEnumType)(errorNode, expandedSubtype, argList);
5901
5954
  }
5902
5955
  if (className === 'TypedDict') {
5903
5956
  return (0, typedDicts_1.createTypedDictType)(evaluatorInterface, errorNode, expandedSubtype, argList);
5904
5957
  }
5905
5958
  if (className === 'auto' && argList.length === 0) {
5906
- return getBuiltInObject(errorNode, 'int');
5959
+ return (0, enums_1.getEnumAutoValueType)(evaluatorInterface, errorNode);
5907
5960
  }
5908
5961
  }
5909
5962
  if (types_1.ClassType.supportsAbstractMethods(expandedSubtype)) {
@@ -6694,7 +6747,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
6694
6747
  reportedArgError = true;
6695
6748
  }
6696
6749
  return {
6697
- type: (0, typeUtils_1.stripLiteralValue)(argType),
6750
+ type: stripLiteralValue(argType),
6698
6751
  isUnbounded: argParam.argument.argumentCategory === 1 /* UnpackedList */,
6699
6752
  };
6700
6753
  });
@@ -7231,7 +7284,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
7231
7284
  // strip literals before performing the assignment. This is used in
7232
7285
  // places like a dict constructor.
7233
7286
  if (argParam.paramCategory === 2 /* VarArgDictionary */ && (0, types_1.isTypeVar)(argParam.paramType)) {
7234
- argType = (0, typeUtils_1.stripLiteralValue)(argType);
7287
+ argType = stripLiteralValue(argType);
7235
7288
  }
7236
7289
  // If there's a constraint filter, apply it to top-level type variables
7237
7290
  // if appropriate. This doesn't properly handle non-top-level constrained
@@ -7545,80 +7598,6 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
7545
7598
  nameParts.push(moduleName);
7546
7599
  return nameParts.reverse().join('.');
7547
7600
  }
7548
- // Creates a new custom enum class with named values.
7549
- function createEnumType(errorNode, enumClass, argList) {
7550
- const fileInfo = AnalyzerNodeInfo.getFileInfo(errorNode);
7551
- let className = 'enum';
7552
- if (argList.length === 0) {
7553
- return undefined;
7554
- }
7555
- else {
7556
- const nameArg = argList[0];
7557
- if (nameArg.argumentCategory === 0 /* Simple */ &&
7558
- nameArg.valueExpression &&
7559
- nameArg.valueExpression.nodeType === 48 /* StringList */) {
7560
- className = nameArg.valueExpression.strings.map((s) => s.value).join('');
7561
- }
7562
- else {
7563
- return undefined;
7564
- }
7565
- }
7566
- const classType = types_1.ClassType.createInstantiable(className, ParseTreeUtils.getClassFullName(errorNode, fileInfo.moduleName, className), fileInfo.moduleName, fileInfo.filePath, 1048576 /* EnumClass */, ParseTreeUtils.getTypeSourceId(errorNode),
7567
- /* declaredMetaclass */ undefined, enumClass.details.effectiveMetaclass);
7568
- classType.details.baseClasses.push(enumClass);
7569
- (0, typeUtils_1.computeMroLinearization)(classType);
7570
- const classFields = classType.details.fields;
7571
- classFields.set('__class__', symbol_1.Symbol.createWithType(4 /* ClassMember */ | 64 /* IgnoredForProtocolMatch */, classType));
7572
- if (argList.length < 2) {
7573
- return undefined;
7574
- }
7575
- else {
7576
- const entriesArg = argList[1];
7577
- if (entriesArg.argumentCategory !== 0 /* Simple */ ||
7578
- !entriesArg.valueExpression ||
7579
- entriesArg.valueExpression.nodeType !== 48 /* StringList */) {
7580
- // Technically, the Enum constructor supports a bunch of different
7581
- // ways to specify the items: space-delimited string, a string
7582
- // iterator, an iterator of name/value tuples, and a dictionary
7583
- // of name/value pairs. We support only the simple space-delimited
7584
- // string here. For users who are interested in type checking, we
7585
- // recommend using the more standard class declaration syntax.
7586
- return undefined;
7587
- }
7588
- else {
7589
- const entries = entriesArg.valueExpression.strings
7590
- .map((s) => s.value)
7591
- .join('')
7592
- .split(' ');
7593
- entries.forEach((entryName) => {
7594
- entryName = entryName.trim();
7595
- if (entryName) {
7596
- const entryType = types_1.UnknownType.create();
7597
- const newSymbol = symbol_1.Symbol.createWithType(4 /* ClassMember */, entryType);
7598
- // We need to associate the declaration with a parse node.
7599
- // In this case it's just part of a string literal value.
7600
- // The definition provider won't necessarily take the
7601
- // user to the exact spot in the string, but it's close enough.
7602
- const stringNode = entriesArg.valueExpression;
7603
- (0, debug_1.assert)(stringNode.nodeType === 48 /* StringList */);
7604
- const fileInfo = AnalyzerNodeInfo.getFileInfo(errorNode);
7605
- const declaration = {
7606
- type: 1 /* Variable */,
7607
- node: stringNode,
7608
- isRuntimeTypeExpression: true,
7609
- path: fileInfo.filePath,
7610
- range: (0, positionUtils_1.convertOffsetsToRange)(stringNode.start, textRange_1.TextRange.getEnd(stringNode), fileInfo.lines),
7611
- moduleName: fileInfo.moduleName,
7612
- isInExceptSuite: false,
7613
- };
7614
- newSymbol.addDeclaration(declaration);
7615
- classFields.set(entryName, newSymbol);
7616
- }
7617
- });
7618
- }
7619
- }
7620
- return classType;
7621
- }
7622
7601
  // Implements the semantics of the NewType call as documented
7623
7602
  // in the Python specification: The static type checker will treat
7624
7603
  // the new type as if it were a subclass of the original type.
@@ -8519,8 +8498,8 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
8519
8498
  isIncomplete = true;
8520
8499
  }
8521
8500
  // Strip any literal values.
8522
- keyTypes = keyTypes.map((t) => (0, typeUtils_1.stripLiteralValue)(t));
8523
- valueTypes = valueTypes.map((t) => (0, typeUtils_1.stripLiteralValue)(t));
8501
+ keyTypes = keyTypes.map((t) => stripLiteralValue(t));
8502
+ valueTypes = valueTypes.map((t) => stripLiteralValue(t));
8524
8503
  keyType = keyTypes.length > 0 ? (0, types_1.combineTypes)(keyTypes) : fallbackType;
8525
8504
  // If the value type differs and we're not using "strict inference mode",
8526
8505
  // we need to back off because we can't properly represent the mappings
@@ -8748,7 +8727,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
8748
8727
  entryTypes.push(entryTypeResult.type);
8749
8728
  }
8750
8729
  });
8751
- entryTypes = entryTypes.map((t) => (0, typeUtils_1.stripLiteralValue)(t));
8730
+ entryTypes = entryTypes.map((t) => stripLiteralValue(t));
8752
8731
  let inferredEntryType = hasExpectedType ? types_1.AnyType.create() : types_1.UnknownType.create();
8753
8732
  if (entryTypes.length > 0) {
8754
8733
  const fileInfo = AnalyzerNodeInfo.getFileInfo(node);
@@ -8806,7 +8785,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
8806
8785
  if (useSynthesizedTypeVar) {
8807
8786
  typeVarContext.setTypeVarType(targetTypeVar, isNarrowable ? undefined : expectedType, expectedType);
8808
8787
  }
8809
- if (entryTypes.every((entryType) => assignType(targetTypeVar, (0, typeUtils_1.stripLiteralValue)(entryType), /* diag */ undefined, typeVarContext))) {
8788
+ if (entryTypes.every((entryType) => assignType(targetTypeVar, stripLiteralValue(entryType), /* diag */ undefined, typeVarContext))) {
8810
8789
  return (0, typeUtils_1.applySolvedTypeVars)(targetTypeVar, typeVarContext);
8811
8790
  }
8812
8791
  // Allocate a fresh typeVarContext before we try again with literals not stripped.
@@ -9080,7 +9059,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
9080
9059
  if (iterableTypeResult.isIncomplete) {
9081
9060
  isIncomplete = true;
9082
9061
  }
9083
- const iterableType = (0, typeUtils_1.stripLiteralValue)(iterableTypeResult.type);
9062
+ const iterableType = stripLiteralValue(iterableTypeResult.type);
9084
9063
  const itemType = (_a = getTypeOfIterator(iterableType, !!node.isAsync, node.iterableExpression)) !== null && _a !== void 0 ? _a : types_1.UnknownType.create();
9085
9064
  const targetExpr = node.targetExpression;
9086
9065
  assignTypeToExpression(targetExpr, itemType, !!iterableTypeResult.isIncomplete, node.iterableExpression);
@@ -9116,7 +9095,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
9116
9095
  }
9117
9096
  let keyType = keyTypeResult.type;
9118
9097
  if (!expectedKeyType || !(0, typeUtils_1.containsLiteralType)(expectedKeyType)) {
9119
- keyType = (0, typeUtils_1.stripLiteralValue)(keyType);
9098
+ keyType = stripLiteralValue(keyType);
9120
9099
  }
9121
9100
  const valueTypeResult = getTypeOfExpression(node.expression.valueExpression,
9122
9101
  /* flags */ undefined, expectedValueOrElementType);
@@ -9125,7 +9104,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
9125
9104
  }
9126
9105
  let valueType = valueTypeResult.type;
9127
9106
  if (!expectedValueOrElementType || !(0, typeUtils_1.containsLiteralType)(expectedValueOrElementType)) {
9128
- valueType = (0, typeUtils_1.stripLiteralValue)(valueType);
9107
+ valueType = stripLiteralValue(valueType);
9129
9108
  }
9130
9109
  type = makeTupleObject([keyType, valueType]);
9131
9110
  }
@@ -9856,49 +9835,6 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
9856
9835
  }
9857
9836
  return createSpecialType(classType, typeArgs, /* paramLimit */ undefined, /* allowParamSpec */ true);
9858
9837
  }
9859
- function transformTypeForPossibleEnumClass(node, getValueType) {
9860
- var _a, _b, _c, _d;
9861
- // If the node is within a class that derives from the metaclass
9862
- // "EnumMeta", we need to treat assignments differently.
9863
- const enclosingClassNode = ParseTreeUtils.getEnclosingClass(node, /* stopAtFunction */ true);
9864
- if (enclosingClassNode) {
9865
- const enumClassInfo = getTypeOfClass(enclosingClassNode);
9866
- if (enumClassInfo && types_1.ClassType.isEnumClass(enumClassInfo.classType)) {
9867
- // In ".py" files, the transform applies only to members that are
9868
- // assigned within the class. In stub files, it applies to most variables
9869
- // even if they are not assigned. This unfortunate convention means
9870
- // there is no way in a stub to specify both enum members and instance
9871
- // variables used within each enum instance. Unless/until there is
9872
- // a change to this convention and all type checkers and stubs adopt
9873
- // it, we're stuck with this limitation.
9874
- let isMemberOfEnumeration = (((_a = node.parent) === null || _a === void 0 ? void 0 : _a.nodeType) === 3 /* Assignment */ && node.parent.leftExpression === node) ||
9875
- (((_b = node.parent) === null || _b === void 0 ? void 0 : _b.nodeType) === 54 /* TypeAnnotation */ &&
9876
- node.parent.valueExpression === node &&
9877
- ((_c = node.parent.parent) === null || _c === void 0 ? void 0 : _c.nodeType) === 3 /* Assignment */) ||
9878
- (AnalyzerNodeInfo.getFileInfo(node).isStubFile &&
9879
- ((_d = node.parent) === null || _d === void 0 ? void 0 : _d.nodeType) === 54 /* TypeAnnotation */ &&
9880
- node.parent.valueExpression === node);
9881
- // The spec specifically excludes names that start and end with a single underscore.
9882
- // This also includes dunder names.
9883
- if ((0, symbolNameUtils_1.isSingleDunderName)(node.value)) {
9884
- isMemberOfEnumeration = false;
9885
- }
9886
- // Specifically exclude "value" and "name". These are reserved by the enum metaclass.
9887
- if (node.value === 'name' || node.value === 'value') {
9888
- isMemberOfEnumeration = false;
9889
- }
9890
- const valueType = getValueType();
9891
- // The spec excludes descriptors.
9892
- if ((0, types_1.isClassInstance)(valueType) && valueType.details.fields.get('__get__')) {
9893
- isMemberOfEnumeration = false;
9894
- }
9895
- if (isMemberOfEnumeration) {
9896
- return types_1.ClassType.cloneAsInstance(types_1.ClassType.cloneWithLiteral(enumClassInfo.classType, new types_1.EnumLiteral(enumClassInfo.classType.details.name, node.value, valueType)));
9897
- }
9898
- }
9899
- }
9900
- return undefined;
9901
- }
9902
9838
  function transformTypeForTypeAlias(type, name, errorNode, typeParameters) {
9903
9839
  if (!types_1.TypeBase.isInstantiable(type)) {
9904
9840
  return type;
@@ -10188,7 +10124,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
10188
10124
  rightHandType = srcType;
10189
10125
  if (node.leftExpression.nodeType === 38 /* Name */ && !node.typeAnnotationComment) {
10190
10126
  rightHandType =
10191
- transformTypeForPossibleEnumClass(node.leftExpression, () => rightHandType) || rightHandType;
10127
+ (0, enums_1.transformTypeForPossibleEnumClass)(evaluatorInterface, node.leftExpression, () => rightHandType) || rightHandType;
10192
10128
  }
10193
10129
  if (typeAliasNameNode) {
10194
10130
  // Clear out the temporary types we wrote above.
@@ -10292,6 +10228,9 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
10292
10228
  const destTypeResult = getTypeOfAugmentedAssignment(node, /* expectedType */ undefined);
10293
10229
  writeTypeCache(node, destTypeResult.type, 0 /* None */, !!destTypeResult.isIncomplete);
10294
10230
  }
10231
+ function getPseudoGenericTypeVarName(paramName) {
10232
+ return `__type_of_${paramName}`;
10233
+ }
10295
10234
  function getTypeOfClass(node) {
10296
10235
  // Is this type already cached?
10297
10236
  const cachedClassType = readTypeCache(node.name, 0 /* None */);
@@ -10605,13 +10544,16 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
10605
10544
  const initParams = initDeclNode.parameters;
10606
10545
  if (initParams.length > 1 &&
10607
10546
  !initParams.some((param, index) => !!ParseTreeUtils.getTypeAnnotationForParameter(initDeclNode, index))) {
10608
- const genericParams = initParams.filter((param, index) => index > 0 && param.name && param.category === 0 /* Simple */);
10547
+ const genericParams = initParams.filter((param, index) => index > 0 &&
10548
+ param.name &&
10549
+ param.category === 0 /* Simple */ &&
10550
+ !param.defaultValue);
10609
10551
  if (genericParams.length > 0) {
10610
10552
  classType.details.flags |= 16384 /* PseudoGenericClass */;
10611
10553
  // Create a type parameter for each simple, named parameter
10612
10554
  // in the __init__ method.
10613
10555
  classType.details.typeParameters = genericParams.map((param) => {
10614
- const typeVar = types_1.TypeVarType.createInstance(`__type_of_${param.name.value}`);
10556
+ const typeVar = types_1.TypeVarType.createInstance(getPseudoGenericTypeVarName(param.name.value));
10615
10557
  typeVar.details.isSynthesized = true;
10616
10558
  typeVar.scopeId = getScopeIdForNode(initDeclNode);
10617
10559
  typeVar.details.boundType = types_1.UnknownType.create();
@@ -11145,7 +11087,6 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
11145
11087
  types_1.ClassType.isPseudoGenericClass(containingClassType) &&
11146
11088
  node.name.value === '__init__';
11147
11089
  const paramTypes = [];
11148
- let typeParamIndex = 0;
11149
11090
  // Determine if the first parameter should be skipped for comment-based
11150
11091
  // function annotations.
11151
11092
  let firstCommentAnnotationIndex = 0;
@@ -11228,9 +11169,9 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
11228
11169
  }
11229
11170
  }
11230
11171
  if (!annotatedType && addGenericParamTypes) {
11231
- if (index > 0 && param.category === 0 /* Simple */ && param.name) {
11232
- annotatedType = containingClassType.details.typeParameters[typeParamIndex];
11233
- typeParamIndex++;
11172
+ if (index > 0 && param.category === 0 /* Simple */ && param.name && !param.defaultValue) {
11173
+ const typeParamName = getPseudoGenericTypeVarName(param.name.value);
11174
+ annotatedType = containingClassType.details.typeParameters.find((param) => param.details.name === typeParamName);
11234
11175
  }
11235
11176
  }
11236
11177
  if (annotatedType) {
@@ -11519,7 +11460,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
11519
11460
  // more restrictive (narrower) than intended.
11520
11461
  if (!(0, types_1.isClassInstance)(defaultValueType) ||
11521
11462
  !types_1.ClassType.isBuiltIn(defaultValueType, ['tuple', 'list', 'set', 'dict'])) {
11522
- inferredParamType = (0, typeUtils_1.stripLiteralValue)(defaultValueType);
11463
+ inferredParamType = stripLiteralValue(defaultValueType);
11523
11464
  }
11524
11465
  }
11525
11466
  if (inferredParamType) {
@@ -11864,7 +11805,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
11864
11805
  if (inferredReturnType) {
11865
11806
  return { type: inferredReturnType, isIncomplete };
11866
11807
  }
11867
- if (functionRecursionMap.has(node.id) && functionRecursionMap.size < maxInferFunctionReturnRecursionCount) {
11808
+ if (functionRecursionMap.has(node.id) || functionRecursionMap.size >= maxInferFunctionReturnRecursionCount) {
11868
11809
  inferredReturnType = types_1.UnknownType.create();
11869
11810
  isIncomplete = true;
11870
11811
  }
@@ -12482,6 +12423,13 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
12482
12423
  // The left expression of a call or member access expression is not contextual.
12483
12424
  if (parent.nodeType === 9 /* Call */ || parent.nodeType === 35 /* MemberAccess */) {
12484
12425
  if (nodeToEvaluate === parent.leftExpression) {
12426
+ // Handle the special case where the LHS is a call to super().
12427
+ if (nodeToEvaluate.nodeType === 9 /* Call */ &&
12428
+ nodeToEvaluate.leftExpression.nodeType === 38 /* Name */ &&
12429
+ nodeToEvaluate.leftExpression.value === 'super') {
12430
+ nodeToEvaluate = parent;
12431
+ continue;
12432
+ }
12485
12433
  flags = 2 /* DoNotSpecialize */;
12486
12434
  break;
12487
12435
  }
@@ -12637,24 +12585,23 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
12637
12585
  return;
12638
12586
  }
12639
12587
  const containingClassNode = ParseTreeUtils.getEnclosingClass(functionNode, /* stopAtFunction */ true);
12640
- if (containingClassNode) {
12641
- const classInfo = getTypeOfClass(containingClassNode);
12642
- if (classInfo) {
12643
- // See if the function is a method in a child class. We may be able to
12644
- // infer the type of the parameter from a method of the same name in
12645
- // a parent class if it has an annotated type.
12646
- const functionFlags = getFunctionFlagsFromDecorators(functionNode, /* isInClass */ true);
12647
- const inferredParamType = inferParameterType(functionNode, functionFlags, paramIndex, classInfo.classType);
12648
- if (inferredParamType) {
12649
- writeTypeCache(node.name, transformVariadicParamType(node, node.category, inferredParamType), 0 /* None */,
12650
- /* isIncomplete */ false);
12651
- return;
12652
- }
12588
+ const classInfo = containingClassNode ? getTypeOfClass(containingClassNode) : undefined;
12589
+ if (classInfo &&
12590
+ types_1.ClassType.isPseudoGenericClass(classInfo === null || classInfo === void 0 ? void 0 : classInfo.classType) &&
12591
+ functionNode.name.value === '__init__') {
12592
+ const typeParamName = getPseudoGenericTypeVarName(node.name.value);
12593
+ const paramType = classInfo.classType.details.typeParameters.find((param) => param.details.name === typeParamName);
12594
+ if (paramType) {
12595
+ writeTypeCache(node.name, paramType, 0 /* None */, /* isIncomplete */ false);
12596
+ return;
12653
12597
  }
12654
12598
  }
12655
- // We weren't able to infer the input parameter type. Set its
12656
- // type to unknown.
12657
- writeTypeCache(node.name, transformVariadicParamType(node, node.category, types_1.UnknownType.create()), 0 /* None */,
12599
+ // See if the function is a method in a child class. We may be able to
12600
+ // infer the type of the parameter from a method of the same name in
12601
+ // a parent class if it has an annotated type.
12602
+ const functionFlags = getFunctionFlagsFromDecorators(functionNode, /* isInClass */ true);
12603
+ const inferredParamType = inferParameterType(functionNode, functionFlags, paramIndex, classInfo === null || classInfo === void 0 ? void 0 : classInfo.classType);
12604
+ writeTypeCache(node.name, transformVariadicParamType(node, node.category, inferredParamType !== null && inferredParamType !== void 0 ? inferredParamType : types_1.UnknownType.create()), 0 /* None */,
12658
12605
  /* isIncomplete */ false);
12659
12606
  }
12660
12607
  // Evaluates the types that are assigned within the statement that contains
@@ -13695,7 +13642,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
13695
13642
  // Apply enum transform if appropriate.
13696
13643
  if (declaration.node.nodeType === 38 /* Name */) {
13697
13644
  declaredType =
13698
- transformTypeForPossibleEnumClass(declaration.node, () => declaredType) || declaredType;
13645
+ (0, enums_1.transformTypeForPossibleEnumClass)(evaluatorInterface, declaration.node, () => declaredType) || declaredType;
13699
13646
  }
13700
13647
  if (typeAliasNode && typeAliasNode.valueExpression.nodeType === 38 /* Name */) {
13701
13648
  declaredType = transformTypeForTypeAlias(declaredType, typeAliasNode.valueExpression, declaration.node);
@@ -13826,7 +13773,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
13826
13773
  })) === null || _b === void 0 ? void 0 : _b.type;
13827
13774
  if (inferredType && resolvedDecl.node.nodeType === 38 /* Name */) {
13828
13775
  // See if this is an enum member. If so, we need to handle it as a special case.
13829
- const enumMemberType = transformTypeForPossibleEnumClass(resolvedDecl.node, () => {
13776
+ const enumMemberType = (0, enums_1.transformTypeForPossibleEnumClass)(evaluatorInterface, resolvedDecl.node, () => {
13830
13777
  var _a, _b;
13831
13778
  return ((_b = (_a = evaluateTypeForSubnode(resolvedDecl.inferredTypeSource, () => {
13832
13779
  evaluateTypesForStatement(resolvedDecl.inferredTypeSource);
@@ -14051,13 +13998,15 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
14051
13998
  let isConstant = decl.type === 1 /* Variable */ && !!decl.isConstant;
14052
13999
  // Treat enum values declared within an enum class as though they are const even
14053
14000
  // though they may not be named as such.
14054
- if ((0, types_1.isClassInstance)(type) && types_1.ClassType.isEnumClass(type) && isDeclInEnumClass(decl)) {
14001
+ if ((0, types_1.isClassInstance)(type) &&
14002
+ types_1.ClassType.isEnumClass(type) &&
14003
+ (0, enums_1.isDeclInEnumClass)(evaluatorInterface, decl)) {
14055
14004
  isConstant = true;
14056
14005
  }
14057
14006
  // If the symbol is constant, we can retain the literal
14058
14007
  // value. Otherwise, strip literal values to widen the type.
14059
14008
  if (types_1.TypeBase.isInstance(type) && !isExplicitTypeAlias && !isConstant && !isFinalVar) {
14060
- type = (0, typeUtils_1.stripLiteralValue)(type);
14009
+ type = stripLiteralValue(type);
14061
14010
  }
14062
14011
  }
14063
14012
  typesToCombine.push(type);
@@ -14178,17 +14127,6 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
14178
14127
  }
14179
14128
  return undefined;
14180
14129
  }
14181
- function isDeclInEnumClass(decl) {
14182
- const classNode = ParseTreeUtils.getEnclosingClass(decl.node, /* stopAtFunction */ true);
14183
- if (!classNode) {
14184
- return false;
14185
- }
14186
- const classInfo = getTypeOfClass(classNode);
14187
- if (!classInfo) {
14188
- return false;
14189
- }
14190
- return types_1.ClassType.isEnumClass(classInfo.classType);
14191
- }
14192
14130
  function inferReturnTypeIfNecessary(type) {
14193
14131
  if ((0, types_1.isFunction)(type)) {
14194
14132
  getFunctionEffectiveReturnType(type);
@@ -14443,7 +14381,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
14443
14381
  }
14444
14382
  return types_1.UnknownType.create();
14445
14383
  }
14446
- function getTypeOfMemberInternal(node, member, selfClass) {
14384
+ function getTypeOfMemberInternal(member, selfClass) {
14447
14385
  if ((0, types_1.isInstantiableClass)(member.classType)) {
14448
14386
  const typeResult = getEffectiveTypeOfSymbolForUsage(member.symbol);
14449
14387
  if (typeResult) {
@@ -14631,7 +14569,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
14631
14569
  const removedArgs = srcTypeArgs.splice(destVariadicIndex, srcArgsToCapture);
14632
14570
  // Package up the remaining type arguments into a tuple object.
14633
14571
  const variadicTuple = (0, typeUtils_1.convertToInstance)((0, typeUtils_1.specializeTupleClass)(tupleClassType, removedArgs.map((typeArg) => {
14634
- return { type: (0, typeUtils_1.stripLiteralValue)(typeArg.type), isUnbounded: false };
14572
+ return { type: stripLiteralValue(typeArg.type), isUnbounded: false };
14635
14573
  }),
14636
14574
  /* isTypeArgumentExplicit */ true,
14637
14575
  /* isUnpackedTuple */ true));
@@ -15191,7 +15129,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
15191
15129
  }
15192
15130
  }
15193
15131
  }
15194
- const concreteSrcType = makeTopLevelTypeVarsConcrete(srcType);
15132
+ let concreteSrcType = makeTopLevelTypeVarsConcrete(srcType);
15195
15133
  if ((0, types_1.isClass)(concreteSrcType) && types_1.TypeBase.isInstance(concreteSrcType)) {
15196
15134
  if (destType.literalValue !== undefined) {
15197
15135
  const srcLiteral = concreteSrcType.literalValue;
@@ -15204,15 +15142,18 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
15204
15142
  }
15205
15143
  }
15206
15144
  // Handle LiteralString special form.
15207
- if (types_1.ClassType.isBuiltIn(destType, 'LiteralString') && types_1.ClassType.isBuiltIn(concreteSrcType, 'str')) {
15208
- if (concreteSrcType.literalValue !== undefined) {
15145
+ if (types_1.ClassType.isBuiltIn(destType, 'LiteralString')) {
15146
+ if (types_1.ClassType.isBuiltIn(concreteSrcType, 'str') && concreteSrcType.literalValue !== undefined) {
15147
+ return true;
15148
+ }
15149
+ else if (types_1.ClassType.isBuiltIn(concreteSrcType, 'LiteralString')) {
15209
15150
  return true;
15210
15151
  }
15211
15152
  }
15212
15153
  else if (types_1.ClassType.isBuiltIn(concreteSrcType, 'LiteralString') &&
15213
- types_1.ClassType.isBuiltIn(destType, 'str') &&
15214
- destType.literalValue === undefined) {
15215
- return true;
15154
+ strClassType &&
15155
+ (0, types_1.isInstantiableClass)(strClassType)) {
15156
+ concreteSrcType = types_1.ClassType.cloneAsInstance(strClassType);
15216
15157
  }
15217
15158
  if (!assignClass(types_1.ClassType.cloneAsInstantiable(destType), types_1.ClassType.cloneAsInstantiable(concreteSrcType), diag, destTypeVarContext, srcTypeVarContext, flags, recursionCount,
15218
15159
  /* reportErrorsUsingObjType */ true)) {
@@ -15600,7 +15541,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
15600
15541
  // contents of the table.
15601
15542
  let typeVarContextScore = destTypeVarContextClone.getScore();
15602
15543
  // If the type matches exactly, prefer it over other types.
15603
- if ((0, types_1.isTypeSame)(subtype, (0, typeUtils_1.stripLiteralValue)(srcType))) {
15544
+ if ((0, types_1.isTypeSame)(subtype, stripLiteralValue(srcType))) {
15604
15545
  typeVarContextScore = Number.POSITIVE_INFINITY;
15605
15546
  }
15606
15547
  if (bestTypeVarContextScore === undefined ||
@@ -16937,9 +16878,6 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
16937
16878
  if (firstParamType && memberType.details.parameters.length > 0) {
16938
16879
  const memberTypeFirstParam = memberType.details.parameters[0];
16939
16880
  const memberTypeFirstParamType = types_1.FunctionType.getEffectiveParameterType(memberType, 0);
16940
- // If the type has a literal associated with it, strip it now. This
16941
- // is needed to handle generic functions in the enum.Flag class.
16942
- const nonLiteralFirstParamType = (0, typeUtils_1.stripLiteralValue)(firstParamType);
16943
16881
  // Fill out the typeVarContext for the "self" or "cls" parameter.
16944
16882
  typeVarContext.addSolveForScope((0, typeUtils_1.getTypeVarScopeId)(memberType));
16945
16883
  const diag = new diagnostic_1.DiagnosticAddendum();
@@ -16953,11 +16891,11 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
16953
16891
  // Instead, we'll assume it's assignable.
16954
16892
  if (!typeVarContext.isLocked()) {
16955
16893
  typeVarContext.setTypeVarType(memberTypeFirstParamType, types_1.TypeBase.isInstantiable(memberTypeFirstParamType)
16956
- ? (0, typeUtils_1.convertToInstance)(nonLiteralFirstParamType)
16957
- : nonLiteralFirstParamType);
16894
+ ? (0, typeUtils_1.convertToInstance)(firstParamType)
16895
+ : firstParamType);
16958
16896
  }
16959
16897
  }
16960
- else if (!assignType(memberTypeFirstParamType, nonLiteralFirstParamType, diag, typeVarContext,
16898
+ else if (!assignType(memberTypeFirstParamType, firstParamType, diag, typeVarContext,
16961
16899
  /* srcTypeVarContext */ undefined, 0 /* Default */, recursionCount)) {
16962
16900
  if (memberTypeFirstParam.name &&
16963
16901
  !memberTypeFirstParam.isNameSynthesized &&
@@ -17062,6 +17000,7 @@ function createTypeEvaluator(importLookup, evaluatorOptions) {
17062
17000
  evaluateTypeOfParameter,
17063
17001
  canBeTruthy,
17064
17002
  canBeFalsy,
17003
+ stripLiteralValue,
17065
17004
  removeTruthinessFromType,
17066
17005
  removeFalsinessFromType,
17067
17006
  verifyRaiseExceptionType,