From 24a25fd79c515050574d94818f7a1d5e65be55b5 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 08:46:47 -0700 Subject: [PATCH 01/56] Revise type inference data structures --- src/compiler/checker.ts | 145 +++++++++++++++++++++------------------- src/compiler/types.ts | 26 ++++--- 2 files changed, 90 insertions(+), 81 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 70403146489..1bba954971a 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -7921,10 +7921,10 @@ namespace ts { function getInferenceMapper(context: InferenceContext): TypeMapper { if (!context.mapper) { const mapper: TypeMapper = t => { - const typeParameters = context.signature.typeParameters; - for (let i = 0; i < typeParameters.length; i++) { - if (t === typeParameters[i]) { - context.inferences[i].isFixed = true; + const inferences = context.inferences; + for (let i = 0; i < inferences.length; i++) { + if (t === inferences[i].typeParameter) { + inferences[i].isFixed = true; return getInferredType(context, i); } } @@ -10131,22 +10131,22 @@ namespace ts { } function createInferenceContext(signature: Signature, inferUnionTypes: boolean, useAnyForNoInferences: boolean): InferenceContext { - const inferences = map(signature.typeParameters, createTypeInferencesObject); return { signature, + inferences: map(signature.typeParameters, createInferenceInfo), inferUnionTypes, - inferences, - inferredTypes: new Array(signature.typeParameters.length), useAnyForNoInferences }; } - function createTypeInferencesObject(): TypeInferences { + function createInferenceInfo(typeParameter: TypeParameter): InferenceInfo { return { - primary: undefined, - secondary: undefined, + typeParameter, + candidates: undefined, + inferredType: undefined, + priority: undefined, topLevel: true, - isFixed: false, + isFixed: false }; } @@ -10183,10 +10183,9 @@ namespace ts { if (properties.length === 0 && !indexInfo) { return undefined; } - const typeVariable = getIndexedAccessType((getConstraintTypeFromMappedType(target)).type, getTypeParameterFromMappedType(target)); - const typeVariableArray = [typeVariable]; - const typeInferences = createTypeInferencesObject(); - const typeInferencesArray = [typeInferences]; + const typeParameter = getIndexedAccessType((getConstraintTypeFromMappedType(target)).type, getTypeParameterFromMappedType(target)); + const inference = createInferenceInfo(typeParameter); + const inferences = [inference]; const templateType = getTemplateTypeFromMappedType(target); const readonlyMask = target.declaration.readonlyToken ? false : true; const optionalMask = target.declaration.questionToken ? 0 : SymbolFlags.Optional; @@ -10212,22 +10211,20 @@ namespace ts { return createAnonymousType(undefined, members, emptyArray, emptyArray, indexInfo, undefined); function inferTargetType(sourceType: Type): Type { - typeInferences.primary = undefined; - typeInferences.secondary = undefined; - inferTypes(typeVariableArray, typeInferencesArray, sourceType, templateType); - const inferences = typeInferences.primary || typeInferences.secondary; - return inferences && getUnionType(inferences, /*subtypeReduction*/ true); + inference.candidates = undefined; + inferTypes(inferences, sourceType, templateType); + return inference.candidates && getUnionType(inference.candidates, /*subtypeReduction*/ true); } } function inferTypesWithContext(context: InferenceContext, originalSource: Type, originalTarget: Type) { - inferTypes(context.signature.typeParameters, context.inferences, originalSource, originalTarget); + inferTypes(context.inferences, originalSource, originalTarget); } - function inferTypes(typeVariables: TypeVariable[], typeInferences: TypeInferences[], originalSource: Type, originalTarget: Type) { + function inferTypes(inferences: InferenceInfo[], originalSource: Type, originalTarget: Type) { let symbolStack: Symbol[]; let visited: Map; - let inferiority = 0; + let priority = 0; inferFromTypes(originalSource, originalTarget); function inferFromTypes(source: Type, target: Type) { @@ -10291,24 +10288,24 @@ namespace ts { if (source.flags & TypeFlags.ContainsAnyFunctionType) { return; } - for (let i = 0; i < typeVariables.length; i++) { - if (target === typeVariables[i]) { - const inferences = typeInferences[i]; - if (!inferences.isFixed) { + for (const inference of inferences) { + if (target === inference.typeParameter) { + if (!inference.isFixed) { // Any inferences that are made to a type parameter in a union type are inferior // to inferences made to a flat (non-union) type. This is because if we infer to // T | string[], we really don't know if we should be inferring to T or not (because // the correct constituent on the target side could be string[]). Therefore, we put // such inferior inferences into a secondary bucket, and only use them if the primary // bucket is empty. - const candidates = inferiority ? - inferences.secondary || (inferences.secondary = []) : - inferences.primary || (inferences.primary = []); - if (!contains(candidates, source)) { - candidates.push(source); + if (!inference.candidates || priority < inference.priority) { + inference.candidates = [source]; + inference.priority = priority; + } + else if (priority === inference.priority) { + inference.candidates.push(source); } if (target.flags & TypeFlags.TypeParameter && !isTypeParameterAtTopLevel(originalTarget, target)) { - inferences.topLevel = false; + inference.topLevel = false; } } return; @@ -10330,7 +10327,7 @@ namespace ts { let typeVariable: TypeVariable; // First infer to each type in union or intersection that isn't a type variable for (const t of targetTypes) { - if (t.flags & TypeFlags.TypeVariable && contains(typeVariables, t)) { + if (getInferenceInfoForType(t)) { typeVariable = t; typeVariableCount++; } @@ -10342,9 +10339,10 @@ namespace ts { // variable. This gives meaningful results for union types in co-variant positions and intersection // types in contra-variant positions (such as callback parameters). if (typeVariableCount === 1) { - inferiority++; + const savePriority = priority; + priority |= InferencePriority.NakedTypeVariable; inferFromTypes(source, typeVariable); - inferiority--; + priority = savePriority; } } else if (source.flags & TypeFlags.UnionOrIntersection) { @@ -10384,6 +10382,17 @@ namespace ts { } } + function getInferenceInfoForType(type: Type) { + if (type.flags & TypeFlags.TypeVariable) { + for (const inference of inferences) { + if (type === inference.typeParameter) { + return inference; + } + } + } + return undefined; + } + function inferFromObjectTypes(source: Type, target: Type) { if (getObjectFlags(target) & ObjectFlags.Mapped) { const constraintType = getConstraintTypeFromMappedType(target); @@ -10392,13 +10401,14 @@ namespace ts { // where T is a type variable. Use inferTypeForHomomorphicMappedType to infer a suitable source // type and then make a secondary inference from that type to T. We make a secondary inference // such that direct inferences to T get priority over inferences to Partial, for example. - const index = indexOf(typeVariables, (constraintType).type); - if (index >= 0 && !typeInferences[index].isFixed) { + const inference = getInferenceInfoForType((constraintType).type); + if (inference && !inference.isFixed) { const inferredType = inferTypeForHomomorphicMappedType(source, target); if (inferredType) { - inferiority++; - inferFromTypes(inferredType, typeVariables[index]); - inferiority--; + const savePriority = priority; + priority |= InferencePriority.MappedType; + inferFromTypes(inferredType, inference.typeParameter); + priority = savePriority; } } return; @@ -10497,33 +10507,29 @@ namespace ts { return type.flags & TypeFlags.Union ? getUnionType(reducedTypes) : getIntersectionType(reducedTypes); } - function getInferenceCandidates(context: InferenceContext, index: number): Type[] { - const inferences = context.inferences[index]; - return inferences.primary || inferences.secondary || emptyArray; - } - function hasPrimitiveConstraint(type: TypeParameter): boolean { const constraint = getConstraintOfTypeParameter(type); return constraint && maybeTypeOfKind(constraint, TypeFlags.Primitive | TypeFlags.Index); } function getInferredType(context: InferenceContext, index: number): Type { - let inferredType = context.inferredTypes[index]; + const inference = context.inferences[index]; + let inferredType = inference.inferredType; let inferenceSucceeded: boolean; if (!inferredType) { - const inferences = getInferenceCandidates(context, index); - if (inferences.length) { + const candidates = inference.candidates; + if (candidates) { // We widen inferred literal types if // all inferences were made to top-level ocurrences of the type parameter, and // the type parameter has no constraint or its constraint includes no primitive or literal types, and // the type parameter was fixed during inference or does not occur at top-level in the return type. const signature = context.signature; - const widenLiteralTypes = context.inferences[index].topLevel && - !hasPrimitiveConstraint(signature.typeParameters[index]) && - (context.inferences[index].isFixed || !isTypeParameterAtTopLevel(getReturnTypeOfSignature(signature), signature.typeParameters[index])); - const baseInferences = widenLiteralTypes ? sameMap(inferences, getWidenedLiteralType) : inferences; + const widenLiteralTypes = inference.topLevel && + !hasPrimitiveConstraint(inference.typeParameter) && + (inference.isFixed || !isTypeParameterAtTopLevel(getReturnTypeOfSignature(signature), inference.typeParameter)); + const baseCandidates = widenLiteralTypes ? sameMap(candidates, getWidenedLiteralType) : candidates; // Infer widened union or supertype, or the unknown type for no common supertype - const unionOrSuperType = context.inferUnionTypes ? getUnionType(baseInferences, /*subtypeReduction*/ true) : getCommonSupertype(baseInferences); + const unionOrSuperType = context.inferUnionTypes ? getUnionType(baseCandidates, /*subtypeReduction*/ true) : getCommonSupertype(baseCandidates); inferredType = unionOrSuperType ? getWidenedType(unionOrSuperType) : unknownType; inferenceSucceeded = !!unionOrSuperType; } @@ -10533,7 +10539,7 @@ namespace ts { // succeeds, meaning there is no error for not having inference candidates. An // inference error only occurs when there are *conflicting* candidates, i.e. // candidates with no common supertype. - const defaultType = getDefaultFromTypeParameter(context.signature.typeParameters[index]); + const defaultType = getDefaultFromTypeParameter(inference.typeParameter); if (defaultType) { // Instantiate the default type. Any forward reference to a type // parameter should be instantiated to the empty object type. @@ -10548,7 +10554,7 @@ namespace ts { inferenceSucceeded = true; } - context.inferredTypes[index] = inferredType; + inference.inferredType = inferredType; // Only do the constraint check if inference succeeded (to prevent cascading errors) if (inferenceSucceeded) { @@ -10556,7 +10562,7 @@ namespace ts { if (constraint) { const instantiatedConstraint = instantiateType(constraint, getInferenceMapper(context)); if (!isTypeAssignableTo(inferredType, getTypeWithThisArgument(instantiatedConstraint, inferredType))) { - context.inferredTypes[index] = inferredType = instantiatedConstraint; + inference.inferredType = inferredType = instantiatedConstraint; } } } @@ -10571,10 +10577,11 @@ namespace ts { } function getInferredTypes(context: InferenceContext): Type[] { - for (let i = 0; i < context.inferredTypes.length; i++) { - getInferredType(context, i); + let result = []; + for (let i = 0; i < context.inferences.length; i++) { + result.push(getInferredType(context, i)); } - return context.inferredTypes; + return result; } // EXPRESSION TYPE CHECKING @@ -14837,18 +14844,18 @@ namespace ts { return getSignatureInstantiation(signature, getInferredTypes(context)); } - function inferTypeArguments(node: CallLikeExpression, signature: Signature, args: Expression[], excludeArgument: boolean[], context: InferenceContext): void { - const typeParameters = signature.typeParameters; + function inferTypeArguments(node: CallLikeExpression, signature: Signature, args: Expression[], excludeArgument: boolean[], context: InferenceContext): Type[] { + const inferences = context.inferences; const inferenceMapper = getInferenceMapper(context); // Clear out all the inference results from the last time inferTypeArguments was called on this context - for (let i = 0; i < typeParameters.length; i++) { + for (let i = 0; i < inferences.length; i++) { // As an optimization, we don't have to clear (and later recompute) inferred types // for type parameters that have already been fixed on the previous call to inferTypeArguments. // It would be just as correct to reset all of them. But then we'd be repeating the same work // for the type parameters that were fixed, namely the work done by getInferredType. - if (!context.inferences[i].isFixed) { - context.inferredTypes[i] = undefined; + if (!inferences[i].isFixed) { + inferences[i].inferredType = undefined; } } @@ -14908,8 +14915,7 @@ namespace ts { } } } - - getInferredTypes(context); + return getInferredTypes(context); } function checkTypeArguments(signature: Signature, typeArgumentNodes: TypeNode[], typeArgumentTypes: Type[], reportErrors: boolean, headMessage?: DiagnosticMessage): boolean { @@ -15491,7 +15497,7 @@ namespace ts { else { Debug.assert(resultOfFailedInference.failedTypeParameterIndex >= 0); const failedTypeParameter = candidateForTypeArgumentError.typeParameters[resultOfFailedInference.failedTypeParameterIndex]; - const inferenceCandidates = getInferenceCandidates(resultOfFailedInference, resultOfFailedInference.failedTypeParameterIndex); + const inferenceCandidates = resultOfFailedInference.inferences[resultOfFailedInference.failedTypeParameterIndex].candidates; let diagnosticChainHead = chainDiagnosticMessages(/*details*/ undefined, // details will be provided by call to reportNoCommonSupertypeError Diagnostics.The_type_argument_for_type_parameter_0_cannot_be_inferred_from_the_usage_Consider_specifying_the_type_arguments_explicitly, @@ -15576,8 +15582,7 @@ namespace ts { typeArgumentsAreValid = checkTypeArguments(candidate, typeArguments, typeArgumentTypes, /*reportErrors*/ false); } else { - inferTypeArguments(node, candidate, args, excludeArgument, inferenceContext); - typeArgumentTypes = inferenceContext.inferredTypes; + typeArgumentTypes = inferTypeArguments(node, candidate, args, excludeArgument, inferenceContext); typeArgumentsAreValid = inferenceContext.failedTypeParameterIndex === undefined; } if (!typeArgumentsAreValid) { diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 4b95c957f74..34aada91f7c 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3341,25 +3341,29 @@ namespace ts { // The identity mapper and regular instantiation mappers do not need it. } - /* @internal */ - export interface TypeInferences { - primary: Type[]; // Inferences made directly to a type parameter - secondary: Type[]; // Inferences made to a type parameter in a union type - topLevel: boolean; // True if all inferences were made from top-level (not nested in object type) locations - isFixed: boolean; // Whether the type parameter is fixed, as defined in section 4.12.2 of the TypeScript spec - // If a type parameter is fixed, no more inferences can be made for the type parameter + export const enum InferencePriority { + NakedTypeVariable = 1 << 0, // Naked type variable in union or intersection type + MappedType = 1 << 1, // Reverse inference for mapped type + } + + export interface InferenceInfo { + typeParameter: TypeParameter; + candidates: Type[]; + inferredType: Type; + priority: InferencePriority; + topLevel: boolean; + isFixed: boolean; } /* @internal */ export interface InferenceContext { signature: Signature; // Generic signature for which inferences are made - inferUnionTypes: boolean; // Infer union types for disjoint candidates (otherwise undefinedType) - inferences: TypeInferences[]; // Inferences made for each type parameter - inferredTypes: Type[]; // Inferred type for each type parameter + inferences: InferenceInfo[]; // Inferences made for each type parameter mapper?: TypeMapper; // Type mapper for this inference context + inferUnionTypes: boolean; // Infer union types for disjoint candidates (otherwise undefinedType) + useAnyForNoInferences: boolean; // Use any instead of {} for no inferences failedTypeParameterIndex?: number; // Index of type parameter for which inference failed // It is optional because in contextual signature instantiation, nothing fails - useAnyForNoInferences?: boolean; // Use any instead of {} for no inferences } /* @internal */ From e19d934b7300125807ab5d4df1b8aff215803476 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 11:59:25 -0700 Subject: [PATCH 02/56] Initial implementation of return type inference --- src/compiler/checker.ts | 60 ++++++++++++++++++++++++++++++++--------- src/compiler/types.ts | 4 ++- 2 files changed, 51 insertions(+), 13 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 1bba954971a..5bd708a2fbc 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -7937,6 +7937,10 @@ namespace ts { return context.mapper; } + function cloneTypeMapper(mapper: TypeMapper): TypeMapper { + return mapper && mapper.context ? getInferenceMapper(cloneInferenceContext(mapper.context)) : mapper; + } + function identityMapper(type: Type): Type { return type; } @@ -10130,12 +10134,13 @@ namespace ts { } } - function createInferenceContext(signature: Signature, inferUnionTypes: boolean, useAnyForNoInferences: boolean): InferenceContext { + function createInferenceContext(callNode: CallLikeExpression, signature: Signature, inferUnionTypes: boolean, noInferenceType: Type): InferenceContext { return { + callNode, signature, inferences: map(signature.typeParameters, createInferenceInfo), inferUnionTypes, - useAnyForNoInferences + noInferenceType }; } @@ -10150,6 +10155,27 @@ namespace ts { }; } + function cloneInferenceContext(context: InferenceContext): InferenceContext { + return { + callNode: context.callNode, + signature: context.signature, + inferences: map(context.inferences, cloneInferenceInfo), + inferUnionTypes: context.inferUnionTypes, + noInferenceType: silentNeverType + } + } + + function cloneInferenceInfo(inference: InferenceInfo): InferenceInfo { + return { + typeParameter: inference.typeParameter, + candidates: inference.candidates && inference.candidates.slice(), + inferredType: inference.inferredType, + priority: inference.priority, + topLevel: inference.topLevel, + isFixed: inference.isFixed + }; + } + // Return true if the given type could possibly reference a type parameter for which // we perform type inference (i.e. a type parameter of a generic function). We cache // results for union and intersection types for performance reasons. @@ -10221,10 +10247,9 @@ namespace ts { inferTypes(context.inferences, originalSource, originalTarget); } - function inferTypes(inferences: InferenceInfo[], originalSource: Type, originalTarget: Type) { + function inferTypes(inferences: InferenceInfo[], originalSource: Type, originalTarget: Type, priority: InferencePriority = 0) { let symbolStack: Symbol[]; let visited: Map; - let priority = 0; inferFromTypes(originalSource, originalTarget); function inferFromTypes(source: Type, target: Type) { @@ -10285,7 +10310,7 @@ namespace ts { // it as an inference candidate. Hopefully, a better candidate will come along that does // not contain anyFunctionType when we come back to this argument for its second round // of inference. - if (source.flags & TypeFlags.ContainsAnyFunctionType) { + if (source.flags & TypeFlags.ContainsAnyFunctionType || source === silentNeverType) { return; } for (const inference of inferences) { @@ -10517,8 +10542,19 @@ namespace ts { let inferredType = inference.inferredType; let inferenceSucceeded: boolean; if (!inferredType) { - const candidates = inference.candidates; - if (candidates) { + if (!inference.candidates && context.callNode && isExpression(context.callNode)) { + const contextualType = getContextualType(context.callNode); + if (contextualType) { + const mapper = cloneTypeMapper(getContextualMapper(context.callNode)); + const instantiatedType = instantiateType(contextualType, mapper); + const returnType = getReturnTypeOfSignature(context.signature); + const saveFixed = inference.isFixed; + inference.isFixed = false; + inferTypes([inference], instantiatedType, returnType, InferencePriority.ReturnType); + inference.isFixed = saveFixed; + } + } + if (inference.candidates) { // We widen inferred literal types if // all inferences were made to top-level ocurrences of the type parameter, and // the type parameter has no constraint or its constraint includes no primitive or literal types, and @@ -10527,7 +10563,7 @@ namespace ts { const widenLiteralTypes = inference.topLevel && !hasPrimitiveConstraint(inference.typeParameter) && (inference.isFixed || !isTypeParameterAtTopLevel(getReturnTypeOfSignature(signature), inference.typeParameter)); - const baseCandidates = widenLiteralTypes ? sameMap(candidates, getWidenedLiteralType) : candidates; + const baseCandidates = widenLiteralTypes ? sameMap(inference.candidates, getWidenedLiteralType) : inference.candidates; // Infer widened union or supertype, or the unknown type for no common supertype const unionOrSuperType = context.inferUnionTypes ? getUnionType(baseCandidates, /*subtypeReduction*/ true) : getCommonSupertype(baseCandidates); inferredType = unionOrSuperType ? getWidenedType(unionOrSuperType) : unknownType; @@ -10539,7 +10575,7 @@ namespace ts { // succeeds, meaning there is no error for not having inference candidates. An // inference error only occurs when there are *conflicting* candidates, i.e. // candidates with no common supertype. - const defaultType = getDefaultFromTypeParameter(inference.typeParameter); + const defaultType = context.noInferenceType === silentNeverType ? undefined : getDefaultFromTypeParameter(inference.typeParameter); if (defaultType) { // Instantiate the default type. Any forward reference to a type // parameter should be instantiated to the empty object type. @@ -10549,7 +10585,7 @@ namespace ts { getInferenceMapper(context))); } else { - inferredType = context.useAnyForNoInferences ? anyType : emptyObjectType; + inferredType = context.noInferenceType; } inferenceSucceeded = true; @@ -14836,7 +14872,7 @@ namespace ts { // Instantiate a generic signature in the context of a non-generic signature (section 3.8.5 in TypeScript spec) function instantiateSignatureInContextOf(signature: Signature, contextualSignature: Signature, contextualMapper: TypeMapper): Signature { - const context = createInferenceContext(signature, /*inferUnionTypes*/ true, /*useAnyForNoInferences*/ false); + const context = createInferenceContext(/*callNode*/ undefined, signature, /*inferUnionTypes*/ true, /*noInferenceType*/ emptyObjectType); forEachMatchingParameterType(contextualSignature, signature, (source, target) => { // Type parameters from outer context referenced by source type are fixed by instantiation of the source type inferTypesWithContext(context, instantiateType(source, contextualMapper), target); @@ -15570,7 +15606,7 @@ namespace ts { let candidate: Signature; let typeArgumentsAreValid: boolean; const inferenceContext = originalCandidate.typeParameters - ? createInferenceContext(originalCandidate, /*inferUnionTypes*/ false, /*useAnyForNoInferences*/ isInJavaScriptFile(node)) + ? createInferenceContext(node, originalCandidate, /*inferUnionTypes*/ false, /*noInferenceType*/ isInJavaScriptFile(node) ? anyType : emptyObjectType) : undefined; while (true) { diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 34aada91f7c..5e5c2851bf8 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3344,6 +3344,7 @@ namespace ts { export const enum InferencePriority { NakedTypeVariable = 1 << 0, // Naked type variable in union or intersection type MappedType = 1 << 1, // Reverse inference for mapped type + ReturnType = 1 << 2, // Inference made from return type of generic function } export interface InferenceInfo { @@ -3357,11 +3358,12 @@ namespace ts { /* @internal */ export interface InferenceContext { + callNode: CallLikeExpression; // Call expression node for which inferences are made signature: Signature; // Generic signature for which inferences are made inferences: InferenceInfo[]; // Inferences made for each type parameter mapper?: TypeMapper; // Type mapper for this inference context inferUnionTypes: boolean; // Infer union types for disjoint candidates (otherwise undefinedType) - useAnyForNoInferences: boolean; // Use any instead of {} for no inferences + noInferenceType: Type; // Type to use for no inferences failedTypeParameterIndex?: number; // Index of type parameter for which inference failed // It is optional because in contextual signature instantiation, nothing fails } From 68056d52c43e8a04c68980049a60aaa9e92329da Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 14:55:27 -0700 Subject: [PATCH 03/56] Clean up implementation --- src/compiler/checker.ts | 92 +++++++++++++++++++++-------------------- src/compiler/types.ts | 9 +++- 2 files changed, 55 insertions(+), 46 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 5bd708a2fbc..222eb4601d9 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10134,13 +10134,12 @@ namespace ts { } } - function createInferenceContext(callNode: CallLikeExpression, signature: Signature, inferUnionTypes: boolean, noInferenceType: Type): InferenceContext { + function createInferenceContext(callNode: CallLikeExpression, signature: Signature, flags: InferenceFlags): InferenceContext { return { callNode, signature, inferences: map(signature.typeParameters, createInferenceInfo), - inferUnionTypes, - noInferenceType + flags, }; } @@ -10160,8 +10159,7 @@ namespace ts { callNode: context.callNode, signature: context.signature, inferences: map(context.inferences, cloneInferenceInfo), - inferUnionTypes: context.inferUnionTypes, - noInferenceType: silentNeverType + flags: context.flags | InferenceFlags.NoDefault, } } @@ -10243,10 +10241,6 @@ namespace ts { } } - function inferTypesWithContext(context: InferenceContext, originalSource: Type, originalTarget: Type) { - inferTypes(context.inferences, originalSource, originalTarget); - } - function inferTypes(inferences: InferenceInfo[], originalSource: Type, originalTarget: Type, priority: InferencePriority = 0) { let symbolStack: Symbol[]; let visited: Map; @@ -10315,13 +10309,10 @@ namespace ts { } for (const inference of inferences) { if (target === inference.typeParameter) { - if (!inference.isFixed) { - // Any inferences that are made to a type parameter in a union type are inferior - // to inferences made to a flat (non-union) type. This is because if we infer to - // T | string[], we really don't know if we should be inferring to T or not (because - // the correct constituent on the target side could be string[]). Therefore, we put - // such inferior inferences into a secondary bucket, and only use them if the primary - // bucket is empty. + // Even if an inference is marked as fixed, we can add candidates from inferences made + // from the return type of generic functions (which only happens when no other candidates + // are present). + if (!inference.isFixed || priority & InferencePriority.ReturnType) { if (!inference.candidates || priority < inference.priority) { inference.candidates = [source]; inference.priority = priority; @@ -10543,15 +10534,21 @@ namespace ts { let inferenceSucceeded: boolean; if (!inferredType) { if (!inference.candidates && context.callNode && isExpression(context.callNode)) { + // We have no inference candidates. Now attempt to get the contextual type for the call + // expression associated with the context, and if a contextual type is available, infer + // from that type to the return type of the call expression. For example, given a + // 'function wrap(cb: (x: T) => U): (x: T) => U' and a call expression + // 'let f: (x: string) => number = wrap(s => s.length)', we infer from the declared type + // of 'f' to the return type of 'wrap'. const contextualType = getContextualType(context.callNode); if (contextualType) { + // We clone the contextual mapper to avoid disturbing a resolution in progress for an + // outer call expression. Effectively we just want a snapshot of whatever has been + // inferred for any outer call expression so far. const mapper = cloneTypeMapper(getContextualMapper(context.callNode)); const instantiatedType = instantiateType(contextualType, mapper); const returnType = getReturnTypeOfSignature(context.signature); - const saveFixed = inference.isFixed; - inference.isFixed = false; inferTypes([inference], instantiatedType, returnType, InferencePriority.ReturnType); - inference.isFixed = saveFixed; } } if (inference.candidates) { @@ -10564,30 +10561,37 @@ namespace ts { !hasPrimitiveConstraint(inference.typeParameter) && (inference.isFixed || !isTypeParameterAtTopLevel(getReturnTypeOfSignature(signature), inference.typeParameter)); const baseCandidates = widenLiteralTypes ? sameMap(inference.candidates, getWidenedLiteralType) : inference.candidates; - // Infer widened union or supertype, or the unknown type for no common supertype - const unionOrSuperType = context.inferUnionTypes ? getUnionType(baseCandidates, /*subtypeReduction*/ true) : getCommonSupertype(baseCandidates); + // Infer widened union or supertype, or the unknown type for no common supertype. We infer union types + // for inferences coming from return types in order to avoid common supertype failures. + const unionOrSuperType = context.flags & InferenceFlags.InferUnionTypes || inference.priority & InferencePriority.ReturnType ? + getUnionType(baseCandidates, /*subtypeReduction*/ true) : getCommonSupertype(baseCandidates); inferredType = unionOrSuperType ? getWidenedType(unionOrSuperType) : unknownType; inferenceSucceeded = !!unionOrSuperType; } else { - // Infer either the default or the empty object type when no inferences were - // made. It is important to remember that in this case, inference still - // succeeds, meaning there is no error for not having inference candidates. An - // inference error only occurs when there are *conflicting* candidates, i.e. - // candidates with no common supertype. - const defaultType = context.noInferenceType === silentNeverType ? undefined : getDefaultFromTypeParameter(inference.typeParameter); - if (defaultType) { - // Instantiate the default type. Any forward reference to a type - // parameter should be instantiated to the empty object type. - inferredType = instantiateType(defaultType, - combineTypeMappers( - createBackreferenceMapper(context.signature.typeParameters, index), - getInferenceMapper(context))); + if (context.flags & InferenceFlags.NoDefault) { + // We use silentNeverType as the wildcard that signals no inferences. + inferredType = silentNeverType; } else { - inferredType = context.noInferenceType; + // Infer either the default or the empty object type when no inferences were + // made. It is important to remember that in this case, inference still + // succeeds, meaning there is no error for not having inference candidates. An + // inference error only occurs when there are *conflicting* candidates, i.e. + // candidates with no common supertype. + const defaultType = getDefaultFromTypeParameter(inference.typeParameter); + if (defaultType) { + // Instantiate the default type. Any forward reference to a type + // parameter should be instantiated to the empty object type. + inferredType = instantiateType(defaultType, + combineTypeMappers( + createBackreferenceMapper(context.signature.typeParameters, index), + getInferenceMapper(context))); + } + else { + inferredType = context.flags & InferenceFlags.AnyDefault ? anyType : emptyObjectType; + } } - inferenceSucceeded = true; } inference.inferredType = inferredType; @@ -14872,10 +14876,10 @@ namespace ts { // Instantiate a generic signature in the context of a non-generic signature (section 3.8.5 in TypeScript spec) function instantiateSignatureInContextOf(signature: Signature, contextualSignature: Signature, contextualMapper: TypeMapper): Signature { - const context = createInferenceContext(/*callNode*/ undefined, signature, /*inferUnionTypes*/ true, /*noInferenceType*/ emptyObjectType); + const context = createInferenceContext(/*callNode*/ undefined, signature, InferenceFlags.InferUnionTypes); forEachMatchingParameterType(contextualSignature, signature, (source, target) => { // Type parameters from outer context referenced by source type are fixed by instantiation of the source type - inferTypesWithContext(context, instantiateType(source, contextualMapper), target); + inferTypes(context.inferences, instantiateType(source, contextualMapper), target); }); return getSignatureInstantiation(signature, getInferredTypes(context)); } @@ -14910,7 +14914,7 @@ namespace ts { if (thisType) { const thisArgumentNode = getThisArgumentOfCall(node); const thisArgumentType = thisArgumentNode ? checkExpression(thisArgumentNode) : voidType; - inferTypesWithContext(context, thisArgumentType, thisType); + inferTypes(context.inferences, thisArgumentType, thisType); } // We perform two passes over the arguments. In the first pass we infer from all arguments, but use @@ -14932,7 +14936,7 @@ namespace ts { argType = checkExpressionWithContextualType(arg, paramType, mapper); } - inferTypesWithContext(context, argType, paramType); + inferTypes(context.inferences, argType, paramType); } } @@ -14947,7 +14951,7 @@ namespace ts { if (excludeArgument[i] === false) { const arg = args[i]; const paramType = getTypeAtPosition(signature, i); - inferTypesWithContext(context, checkExpressionWithContextualType(arg, paramType, inferenceMapper), paramType); + inferTypes(context.inferences, checkExpressionWithContextualType(arg, paramType, inferenceMapper), paramType); } } } @@ -15606,7 +15610,7 @@ namespace ts { let candidate: Signature; let typeArgumentsAreValid: boolean; const inferenceContext = originalCandidate.typeParameters - ? createInferenceContext(node, originalCandidate, /*inferUnionTypes*/ false, /*noInferenceType*/ isInJavaScriptFile(node) ? anyType : emptyObjectType) + ? createInferenceContext(node, originalCandidate, /*flags*/ isInJavaScriptFile(node) ? InferenceFlags.AnyDefault : 0) : undefined; while (true) { @@ -16192,7 +16196,7 @@ namespace ts { for (let i = 0; i < len; i++) { const declaration = signature.parameters[i].valueDeclaration; if (declaration.type) { - inferTypesWithContext(mapper.context, getTypeFromTypeNode(declaration.type), getTypeAtPosition(context, i)); + inferTypes(mapper.context.inferences, getTypeFromTypeNode(declaration.type), getTypeAtPosition(context, i)); } } } @@ -16278,7 +16282,7 @@ namespace ts { // T in the second overload so that we do not infer Base as a candidate for T // (inferring Base would make type argument inference inconsistent between the two // overloads). - inferTypesWithContext(mapper.context, links.type, instantiateType(contextualType, mapper)); + inferTypes(mapper.context.inferences, links.type, instantiateType(contextualType, mapper)); } } diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 5e5c2851bf8..08cccd35d7a 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3356,14 +3356,19 @@ namespace ts { isFixed: boolean; } + export const enum InferenceFlags { + InferUnionTypes = 1 << 0, // Infer union types for disjoint candidates (otherwise unknownType) + NoDefault = 1 << 1, // Infer unknownType for no inferences (otherwise anyType or emptyObjectType) + AnyDefault = 1 << 2, // Infer anyType for no inferences (otherwise emptyObjectType) + } + /* @internal */ export interface InferenceContext { callNode: CallLikeExpression; // Call expression node for which inferences are made signature: Signature; // Generic signature for which inferences are made inferences: InferenceInfo[]; // Inferences made for each type parameter + flags: InferenceFlags; // Infer union types for disjoint candidates (otherwise undefinedType) mapper?: TypeMapper; // Type mapper for this inference context - inferUnionTypes: boolean; // Infer union types for disjoint candidates (otherwise undefinedType) - noInferenceType: Type; // Type to use for no inferences failedTypeParameterIndex?: number; // Index of type parameter for which inference failed // It is optional because in contextual signature instantiation, nothing fails } From 7dd9e2156cb410ecad0d40787e96bf814c467e6d Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 14:56:20 -0700 Subject: [PATCH 04/56] Accept new baselines --- tests/baselines/reference/implicitAnyGenerics.types | 2 +- .../reference/recursiveTypeComparison2.errors.txt | 9 ++------- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/tests/baselines/reference/implicitAnyGenerics.types b/tests/baselines/reference/implicitAnyGenerics.types index 1202c73c51a..e6237e9f3a2 100644 --- a/tests/baselines/reference/implicitAnyGenerics.types +++ b/tests/baselines/reference/implicitAnyGenerics.types @@ -26,7 +26,7 @@ var c3 = new C(); var c4: C = new C(); >c4 : C >C : C ->new C() : C<{}> +>new C() : C >C : typeof C class D { diff --git a/tests/baselines/reference/recursiveTypeComparison2.errors.txt b/tests/baselines/reference/recursiveTypeComparison2.errors.txt index 71f337ad15f..5c1200ceec6 100644 --- a/tests/baselines/reference/recursiveTypeComparison2.errors.txt +++ b/tests/baselines/reference/recursiveTypeComparison2.errors.txt @@ -1,9 +1,7 @@ tests/cases/compiler/recursiveTypeComparison2.ts(13,80): error TS2304: Cannot find name 'StateValue'. -tests/cases/compiler/recursiveTypeComparison2.ts(30,5): error TS2322: Type 'Bus<{}>' is not assignable to type 'Bus'. - Type '{}' is not assignable to type 'number'. -==== tests/cases/compiler/recursiveTypeComparison2.ts (2 errors) ==== +==== tests/cases/compiler/recursiveTypeComparison2.ts (1 errors) ==== // Before fix this would cause compiler to hang (#1170) declare module Bacon { @@ -35,7 +33,4 @@ tests/cases/compiler/recursiveTypeComparison2.ts(30,5): error TS2322: Type 'Bus< var Bus: new () => Bus; } - var stuck: Bacon.Bus = new Bacon.Bus(); - ~~~~~ -!!! error TS2322: Type 'Bus<{}>' is not assignable to type 'Bus'. -!!! error TS2322: Type '{}' is not assignable to type 'number'. \ No newline at end of file + var stuck: Bacon.Bus = new Bacon.Bus(); \ No newline at end of file From 0b37adc3a7fe1cbfa8685818ef92a436e53af773 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 16:48:45 -0700 Subject: [PATCH 05/56] Fix fourslash test --- tests/cases/fourslash/genericCombinators2.ts | 37 ++++++++++---------- 1 file changed, 18 insertions(+), 19 deletions(-) diff --git a/tests/cases/fourslash/genericCombinators2.ts b/tests/cases/fourslash/genericCombinators2.ts index a5cea186789..aedadfa301e 100644 --- a/tests/cases/fourslash/genericCombinators2.ts +++ b/tests/cases/fourslash/genericCombinators2.ts @@ -1,48 +1,48 @@ /// ////interface Collection { -//// length: number; -//// add(x: T, y: U): void ; -//// remove(x: T, y: U): boolean; -////} +//// length: number; +//// add(x: T, y: U): void ; +//// remove(x: T, y: U): boolean; ////} +//// ////interface Combinators { -//// map(c: Collection, f: (x: T, y: U) => V): Collection; -//// map(c: Collection, f: (x: T, y: U) => any): Collection; -////} +//// map(c: Collection, f: (x: T, y: U) => V): Collection; +//// map(c: Collection, f: (x: T, y: U) => any): Collection; ////} +//// ////class A { -//// foo(): T { return null; } -////} +//// foo(): T { return null; } ////} +//// ////class B { -//// foo(x: T): T { return null; } -////} +//// foo(x: T): T { return null; } ////} +//// ////var c1: Collection; ////var c2: Collection; ////var c3: Collection, string>; ////var c4: Collection; ////var c5: Collection>; -////} +//// ////var _: Combinators; ////// param help on open paren for arg 2 should show 'number' not T or 'any' ////// x should be contextually typed to number ////var rf1 = (x: number, y: string) => { return x.toFixed() }; ////var rf2 = (x: Collection, y: string) => { return x.length }; ////var rf3 = (x: number, y: A) => { return y.foo() }; -////} +//// ////var /*9*/r1a = _.map/*1c*/(c2, (/*1a*/x, /*1b*/y) => { return x.toFixed() }); ////var /*10*/r1b = _.map(c2, rf1); -////} +//// ////var /*11*/r2a = _.map(c3, (/*2a*/x, /*2b*/y) => { return x.length }); ////var /*12*/r2b = _.map(c3, rf2); -////} +//// ////var /*13*/r3a = _.map(c4, (/*3a*/x, /*3b*/y) => { return y.foo() }); ////var /*14*/r3b = _.map(c4, rf3); -////} +//// ////var /*15*/r4a = _.map(c5, (/*4a*/x, /*4b*/y) => { return y.foo() }); -////} +//// ////var /*17*/r5a = _.map(c2, /*17error1*/(/*5a*/x, /*5b*/y) => { return x.toFixed() }/*17error2*/); ////var rf1b = (x: number, y: string) => { return new Date() }; ////var /*18*/r5b = _.map(c2, rf1b); @@ -51,7 +51,7 @@ ////var rf2b = (x: Collection, y: string) => { return new Date(); }; ////var /*20*/r6b = _.map, string, Date>(c3, rf2b); //// -////var /*21*/r7a = _.map(c4, /*21error1*/(/*7a*/x,/*7b*/y) => { return y.foo() }/*21error2*/); +////var /*21*/r7a = _.map(c4, (/*7a*/x,/*7b*/y) => { return y.foo() }); ////var /*22*/r7b = _.map(c4, /*22error1*/rf3/*22error2*/); //// ////var /*23*/r8a = _.map(c5, (/*8a*/x,/*8b*/y) => { return y.foo() }); @@ -89,5 +89,4 @@ verify.quickInfos({ verify.errorExistsBetweenMarkers('error1', 'error2'); verify.errorExistsBetweenMarkers('17error1', '17error2'); -verify.errorExistsBetweenMarkers('21error1', '21error2'); verify.errorExistsBetweenMarkers('22error1', '22error2'); \ No newline at end of file From 501d92a0494412ead4728502eb63c226664cb071 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Mon, 22 May 2017 16:48:57 -0700 Subject: [PATCH 06/56] Fix linting errors --- src/compiler/checker.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 8c42d890665..de0feae2f08 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10159,8 +10159,8 @@ namespace ts { callNode: context.callNode, signature: context.signature, inferences: map(context.inferences, cloneInferenceInfo), - flags: context.flags | InferenceFlags.NoDefault, - } + flags: context.flags | InferenceFlags.NoDefault + }; } function cloneInferenceInfo(inference: InferenceInfo): InferenceInfo { @@ -10617,7 +10617,7 @@ namespace ts { } function getInferredTypes(context: InferenceContext): Type[] { - let result = []; + const result: Type[] = []; for (let i = 0; i < context.inferences.length; i++) { result.push(getInferredType(context, i)); } From b0de80f07efb9e6f1ddde1f7e2b471a47f9ec212 Mon Sep 17 00:00:00 2001 From: Andy Hanson Date: Wed, 24 May 2017 08:14:52 -0700 Subject: [PATCH 07/56] Set '.declarations' on a property of a homomorphic mapped type --- src/compiler/checker.ts | 1 + .../server/quickInfoMappedSpreadTypes.ts | 30 +++++++++++++++++++ 2 files changed, 31 insertions(+) create mode 100644 tests/cases/fourslash/server/quickInfoMappedSpreadTypes.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index ce982a113f2..e3aedd5fe51 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -5690,6 +5690,7 @@ namespace ts { prop.type = propType; if (propertySymbol) { prop.syntheticOrigin = propertySymbol; + prop.declarations = propertySymbol.declarations; } members.set(propName, prop); } diff --git a/tests/cases/fourslash/server/quickInfoMappedSpreadTypes.ts b/tests/cases/fourslash/server/quickInfoMappedSpreadTypes.ts new file mode 100644 index 00000000000..2a0c1668763 --- /dev/null +++ b/tests/cases/fourslash/server/quickInfoMappedSpreadTypes.ts @@ -0,0 +1,30 @@ +/// + +////interface Foo { +//// /** Doc */ +//// bar: number; +////} +//// +////const f: Foo = { bar: 0 }; +////f./*f*/bar; +//// +////const f2: { [TKey in keyof Foo]: string } = { bar: "0" }; +////f2./*f2*/bar; +//// +////const f3 = { ...f }; +////f3./*f3*/bar; +//// +////const f4 = { ...f2 }; +////f4./*f4*/bar; + +goTo.marker("f"); +verify.quickInfoIs("(property) Foo.bar: number", "Doc "); + +goTo.marker("f2"); +verify.quickInfoIs("(property) bar: string", "Doc "); + +goTo.marker("f3"); +verify.quickInfoIs("(property) Foo.bar: number", "Doc "); + +goTo.marker("f4"); +verify.quickInfoIs("(property) bar: string", "Doc "); From 77e2f097c36ee66239a1715ac3154c79f457f5e4 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 24 May 2017 10:44:19 -0700 Subject: [PATCH 08/56] InferenceContext is-a TypeMapper instead of has-a TypeMapper --- src/compiler/checker.ts | 71 +++++++++++++++++------------------------ src/compiler/types.ts | 8 ++--- 2 files changed, 32 insertions(+), 47 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index de0feae2f08..e323d97d781 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -7918,27 +7918,14 @@ namespace ts { return mapper; } - function getInferenceMapper(context: InferenceContext): TypeMapper { - if (!context.mapper) { - const mapper: TypeMapper = t => { - const inferences = context.inferences; - for (let i = 0; i < inferences.length; i++) { - if (t === inferences[i].typeParameter) { - inferences[i].isFixed = true; - return getInferredType(context, i); - } - } - return t; - }; - mapper.mappedTypes = context.signature.typeParameters; - mapper.context = context; - context.mapper = mapper; - } - return context.mapper; + function isInferenceContext(mapper: TypeMapper): mapper is InferenceContext { + return !!(mapper).signature; } function cloneTypeMapper(mapper: TypeMapper): TypeMapper { - return mapper && mapper.context ? getInferenceMapper(cloneInferenceContext(mapper.context)) : mapper; + return mapper && isInferenceContext(mapper) ? + createInferenceContext(mapper.callNode, mapper.signature, mapper.flags | InferenceFlags.NoDefault, mapper.inferences) : + mapper; } function identityMapper(type: Type): Type { @@ -10134,13 +10121,25 @@ namespace ts { } } - function createInferenceContext(callNode: CallLikeExpression, signature: Signature, flags: InferenceFlags): InferenceContext { - return { - callNode, - signature, - inferences: map(signature.typeParameters, createInferenceInfo), - flags, - }; + function createInferenceContext(callNode: CallLikeExpression, signature: Signature, flags: InferenceFlags, baseInferences?: InferenceInfo[]): InferenceContext { + const inferences = baseInferences ? map(baseInferences, cloneInferenceInfo) : map(signature.typeParameters, createInferenceInfo); + const context = mapper as InferenceContext; + context.mappedTypes = signature.typeParameters; + context.callNode = callNode; + context.signature = signature; + context.inferences = inferences; + context.flags = flags; + return context; + + function mapper(t: Type): Type { + for (let i = 0; i < inferences.length; i++) { + if (t === inferences[i].typeParameter) { + inferences[i].isFixed = true; + return getInferredType(context, i); + } + } + return t; + } } function createInferenceInfo(typeParameter: TypeParameter): InferenceInfo { @@ -10154,15 +10153,6 @@ namespace ts { }; } - function cloneInferenceContext(context: InferenceContext): InferenceContext { - return { - callNode: context.callNode, - signature: context.signature, - inferences: map(context.inferences, cloneInferenceInfo), - flags: context.flags | InferenceFlags.NoDefault - }; - } - function cloneInferenceInfo(inference: InferenceInfo): InferenceInfo { return { typeParameter: inference.typeParameter, @@ -10586,7 +10576,7 @@ namespace ts { inferredType = instantiateType(defaultType, combineTypeMappers( createBackreferenceMapper(context.signature.typeParameters, index), - getInferenceMapper(context))); + context)); } else { inferredType = context.flags & InferenceFlags.AnyDefault ? anyType : emptyObjectType; @@ -10600,7 +10590,7 @@ namespace ts { if (inferenceSucceeded) { const constraint = getConstraintOfTypeParameter(context.signature.typeParameters[index]); if (constraint) { - const instantiatedConstraint = instantiateType(constraint, getInferenceMapper(context)); + const instantiatedConstraint = instantiateType(constraint, context); if (!isTypeAssignableTo(inferredType, getTypeWithThisArgument(instantiatedConstraint, inferredType))) { inference.inferredType = inferredType = instantiatedConstraint; } @@ -14886,7 +14876,6 @@ namespace ts { function inferTypeArguments(node: CallLikeExpression, signature: Signature, args: Expression[], excludeArgument: boolean[], context: InferenceContext): Type[] { const inferences = context.inferences; - const inferenceMapper = getInferenceMapper(context); // Clear out all the inference results from the last time inferTypeArguments was called on this context for (let i = 0; i < inferences.length; i++) { @@ -14932,7 +14921,7 @@ namespace ts { if (argType === undefined) { // For context sensitive arguments we pass the identityMapper, which is a signal to treat all // context sensitive function expressions as wildcards - const mapper = excludeArgument && excludeArgument[i] !== undefined ? identityMapper : inferenceMapper; + const mapper = excludeArgument && excludeArgument[i] !== undefined ? identityMapper : context; argType = checkExpressionWithContextualType(arg, paramType, mapper); } @@ -14951,7 +14940,7 @@ namespace ts { if (excludeArgument[i] === false) { const arg = args[i]; const paramType = getTypeAtPosition(signature, i); - inferTypes(context.inferences, checkExpressionWithContextualType(arg, paramType, inferenceMapper), paramType); + inferTypes(context.inferences, checkExpressionWithContextualType(arg, paramType, context), paramType); } } } @@ -16196,7 +16185,7 @@ namespace ts { for (let i = 0; i < len; i++) { const declaration = signature.parameters[i].valueDeclaration; if (declaration.type) { - inferTypes(mapper.context.inferences, getTypeFromTypeNode(declaration.type), getTypeAtPosition(context, i)); + inferTypes((mapper).inferences, getTypeFromTypeNode(declaration.type), getTypeAtPosition(context, i)); } } } @@ -16282,7 +16271,7 @@ namespace ts { // T in the second overload so that we do not infer Base as a candidate for T // (inferring Base would make type argument inference inconsistent between the two // overloads). - inferTypes(mapper.context.inferences, links.type, instantiateType(contextualType, mapper)); + inferTypes((mapper).inferences, links.type, instantiateType(contextualType, mapper)); } } diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 08cccd35d7a..9a36f0b285f 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3336,9 +3336,6 @@ namespace ts { (t: TypeParameter): Type; mappedTypes?: Type[]; // Types mapped by this mapper instantiations?: Type[]; // Cache of instantiations created using this type mapper. - context?: InferenceContext; // The inference context this mapper was created from. - // Only inference mappers have this set (in createInferenceMapper). - // The identity mapper and regular instantiation mappers do not need it. } export const enum InferencePriority { @@ -3363,12 +3360,11 @@ namespace ts { } /* @internal */ - export interface InferenceContext { + export interface InferenceContext extends TypeMapper { callNode: CallLikeExpression; // Call expression node for which inferences are made signature: Signature; // Generic signature for which inferences are made inferences: InferenceInfo[]; // Inferences made for each type parameter - flags: InferenceFlags; // Infer union types for disjoint candidates (otherwise undefinedType) - mapper?: TypeMapper; // Type mapper for this inference context + flags: InferenceFlags; // Inference flags failedTypeParameterIndex?: number; // Index of type parameter for which inference failed // It is optional because in contextual signature instantiation, nothing fails } From a2ba649ddd9416c53d951b6512dba157418097df Mon Sep 17 00:00:00 2001 From: Kanchalai Tanglertsampan Date: Wed, 24 May 2017 10:54:08 -0700 Subject: [PATCH 09/56] Fix emit duplicate comment --- src/compiler/emitter.ts | 2 +- tests/baselines/reference/alwaysStrictModule3.js | 1 - tests/baselines/reference/alwaysStrictModule5.js | 1 - tests/baselines/reference/capturedLetConstInLoop4_ES6.js | 1 - 4 files changed, 1 insertion(+), 4 deletions(-) diff --git a/src/compiler/emitter.ts b/src/compiler/emitter.ts index aef1a61e080..1d2f75fcd60 100644 --- a/src/compiler/emitter.ts +++ b/src/compiler/emitter.ts @@ -3011,7 +3011,7 @@ namespace ts { NoInterveningComments = 1 << 17, // Do not emit comments between each node // Precomputed Formats - Modifiers = SingleLine | SpaceBetweenSiblings, + Modifiers = SingleLine | SpaceBetweenSiblings | NoInterveningComments, HeritageClauses = SingleLine | SpaceBetweenSiblings, SingleLineTypeLiteralMembers = SingleLine | SpaceBetweenBraces | SpaceBetweenSiblings | Indented, MultiLineTypeLiteralMembers = MultiLine | Indented, diff --git a/tests/baselines/reference/alwaysStrictModule3.js b/tests/baselines/reference/alwaysStrictModule3.js index 2eb8de84028..9ba8db7052c 100644 --- a/tests/baselines/reference/alwaysStrictModule3.js +++ b/tests/baselines/reference/alwaysStrictModule3.js @@ -4,5 +4,4 @@ export const a = 1; //// [alwaysStrictModule3.js] // module ES2015 -// module ES2015 export var a = 1; diff --git a/tests/baselines/reference/alwaysStrictModule5.js b/tests/baselines/reference/alwaysStrictModule5.js index 2356df0e393..664bc634627 100644 --- a/tests/baselines/reference/alwaysStrictModule5.js +++ b/tests/baselines/reference/alwaysStrictModule5.js @@ -4,5 +4,4 @@ export const a = 1; //// [alwaysStrictModule5.js] // Targeting ES6 -// Targeting ES6 export const a = 1; diff --git a/tests/baselines/reference/capturedLetConstInLoop4_ES6.js b/tests/baselines/reference/capturedLetConstInLoop4_ES6.js index b1b60535475..e7a16aa01c6 100644 --- a/tests/baselines/reference/capturedLetConstInLoop4_ES6.js +++ b/tests/baselines/reference/capturedLetConstInLoop4_ES6.js @@ -144,7 +144,6 @@ for (const y = 0; y < 1;) { //// [capturedLetConstInLoop4_ES6.js] //======let -//======let export function exportedFoo() { return v0 + v00 + v1 + v2 + v3 + v4 + v5 + v6 + v7 + v8; } From b8d5eff8ace9ee4c6dc46a0c80be126c51983756 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 24 May 2017 15:31:10 -0700 Subject: [PATCH 10/56] Move return type inference to inferTypeArguments function --- src/compiler/checker.ts | 49 ++++++++++++++++++++--------------------- src/compiler/types.ts | 1 - 2 files changed, 24 insertions(+), 26 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index e323d97d781..30100332210 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -7924,7 +7924,7 @@ namespace ts { function cloneTypeMapper(mapper: TypeMapper): TypeMapper { return mapper && isInferenceContext(mapper) ? - createInferenceContext(mapper.callNode, mapper.signature, mapper.flags | InferenceFlags.NoDefault, mapper.inferences) : + createInferenceContext(mapper.signature, mapper.flags | InferenceFlags.NoDefault, mapper.inferences) : mapper; } @@ -10121,11 +10121,10 @@ namespace ts { } } - function createInferenceContext(callNode: CallLikeExpression, signature: Signature, flags: InferenceFlags, baseInferences?: InferenceInfo[]): InferenceContext { + function createInferenceContext(signature: Signature, flags: InferenceFlags, baseInferences?: InferenceInfo[]): InferenceContext { const inferences = baseInferences ? map(baseInferences, cloneInferenceInfo) : map(signature.typeParameters, createInferenceInfo); const context = mapper as InferenceContext; context.mappedTypes = signature.typeParameters; - context.callNode = callNode; context.signature = signature; context.inferences = inferences; context.flags = flags; @@ -10302,7 +10301,7 @@ namespace ts { // Even if an inference is marked as fixed, we can add candidates from inferences made // from the return type of generic functions (which only happens when no other candidates // are present). - if (!inference.isFixed || priority & InferencePriority.ReturnType) { + if (!inference.isFixed) { if (!inference.candidates || priority < inference.priority) { inference.candidates = [source]; inference.priority = priority; @@ -10310,7 +10309,7 @@ namespace ts { else if (priority === inference.priority) { inference.candidates.push(source); } - if (target.flags & TypeFlags.TypeParameter && !isTypeParameterAtTopLevel(originalTarget, target)) { + if (!(priority & InferencePriority.ReturnType) && target.flags & TypeFlags.TypeParameter && !isTypeParameterAtTopLevel(originalTarget, target)) { inference.topLevel = false; } } @@ -10523,24 +10522,6 @@ namespace ts { let inferredType = inference.inferredType; let inferenceSucceeded: boolean; if (!inferredType) { - if (!inference.candidates && context.callNode && isExpression(context.callNode)) { - // We have no inference candidates. Now attempt to get the contextual type for the call - // expression associated with the context, and if a contextual type is available, infer - // from that type to the return type of the call expression. For example, given a - // 'function wrap(cb: (x: T) => U): (x: T) => U' and a call expression - // 'let f: (x: string) => number = wrap(s => s.length)', we infer from the declared type - // of 'f' to the return type of 'wrap'. - const contextualType = getContextualType(context.callNode); - if (contextualType) { - // We clone the contextual mapper to avoid disturbing a resolution in progress for an - // outer call expression. Effectively we just want a snapshot of whatever has been - // inferred for any outer call expression so far. - const mapper = cloneTypeMapper(getContextualMapper(context.callNode)); - const instantiatedType = instantiateType(contextualType, mapper); - const returnType = getReturnTypeOfSignature(context.signature); - inferTypes([inference], instantiatedType, returnType, InferencePriority.ReturnType); - } - } if (inference.candidates) { // We widen inferred literal types if // all inferences were made to top-level ocurrences of the type parameter, and @@ -14866,7 +14847,7 @@ namespace ts { // Instantiate a generic signature in the context of a non-generic signature (section 3.8.5 in TypeScript spec) function instantiateSignatureInContextOf(signature: Signature, contextualSignature: Signature, contextualMapper: TypeMapper): Signature { - const context = createInferenceContext(/*callNode*/ undefined, signature, InferenceFlags.InferUnionTypes); + const context = createInferenceContext(signature, InferenceFlags.InferUnionTypes); forEachMatchingParameterType(contextualSignature, signature, (source, target) => { // Type parameters from outer context referenced by source type are fixed by instantiation of the source type inferTypes(context.inferences, instantiateType(source, contextualMapper), target); @@ -14899,6 +14880,24 @@ namespace ts { context.failedTypeParameterIndex = undefined; } + // If a contextual type is available, infer from that type to the return type of the call expression. For + // example, given a 'function wrap(cb: (x: T) => U): (x: T) => U' and a call expression + // 'let f: (x: string) => number = wrap(s => s.length)', we infer from the declared type of 'f' to the + // return type of 'wrap'. + if (isExpression(node)) { + const contextualType = getContextualType(node); + if (contextualType) { + // We clone the contextual mapper to avoid disturbing a resolution in progress for an + // outer call expression. Effectively we just want a snapshot of whatever has been + // inferred for any outer call expression so far. + const mapper = cloneTypeMapper(getContextualMapper(node)); + const instantiatedType = instantiateType(contextualType, mapper); + const returnType = getReturnTypeOfSignature(signature); + // Inferences made from return types have lower priority than all other inferences. + inferTypes(context.inferences, instantiatedType, returnType, InferencePriority.ReturnType); + } + } + const thisType = getThisTypeOfSignature(signature); if (thisType) { const thisArgumentNode = getThisArgumentOfCall(node); @@ -15599,7 +15598,7 @@ namespace ts { let candidate: Signature; let typeArgumentsAreValid: boolean; const inferenceContext = originalCandidate.typeParameters - ? createInferenceContext(node, originalCandidate, /*flags*/ isInJavaScriptFile(node) ? InferenceFlags.AnyDefault : 0) + ? createInferenceContext(originalCandidate, /*flags*/ isInJavaScriptFile(node) ? InferenceFlags.AnyDefault : 0) : undefined; while (true) { diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 9a36f0b285f..d42f975f682 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3361,7 +3361,6 @@ namespace ts { /* @internal */ export interface InferenceContext extends TypeMapper { - callNode: CallLikeExpression; // Call expression node for which inferences are made signature: Signature; // Generic signature for which inferences are made inferences: InferenceInfo[]; // Inferences made for each type parameter flags: InferenceFlags; // Inference flags From f29d7df5d150070eb0e3e4cf49d76560d72ea63b Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 24 May 2017 15:50:30 -0700 Subject: [PATCH 11/56] Add tests --- .../inferFromGenericFunctionReturnTypes1.ts | 70 ++++++++++++++ .../inferFromGenericFunctionReturnTypes2.ts | 94 +++++++++++++++++++ 2 files changed, 164 insertions(+) create mode 100644 tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts create mode 100644 tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts diff --git a/tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts b/tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts new file mode 100644 index 00000000000..3fb454ec7e5 --- /dev/null +++ b/tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts @@ -0,0 +1,70 @@ +// Repro from #15680 + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { + _store: A[]; + + add(a: A) { + this._store.push(a); + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { + return transformer(this); + } + + forEach(fn: (a: A, index: number) => void) { + this._store.forEach((a, i) => fn(a, i)); + } +} + +function compose( + fnA: (a: SetOf) => SetOf, + fnB: (b: SetOf) => SetOf, + fnC: (c: SetOf) => SetOf, + fnD: (c: SetOf) => SetOf, +):(x: SetOf) => SetOf; +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { + return (a: SetOf) => { + const b: SetOf = new SetOf(); + a.forEach(x => b.add(fn(x))); + return b; + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { + return (a: SetOf) => { + const result = new SetOf(); + a.forEach(x => { + if (predicate(x)) result.add(x); + }); + return result; + } +} + +const testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); + +testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) + +testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => 123), // Whoops a bug + map(x => x.toUpperCase()) // causes an error! + ) +) diff --git a/tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts b/tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts new file mode 100644 index 00000000000..314159d363c --- /dev/null +++ b/tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts @@ -0,0 +1,94 @@ +type Mapper = (x: T) => U; + +declare function wrap(cb: Mapper): Mapper; + +declare function arrayize(cb: Mapper): Mapper; + +declare function combine(f: (x: A) => B, g: (x: B) => C): (x: A) => C; + +declare function foo(f: Mapper): void; + +let f1: Mapper = s => s.length; +let f2: Mapper = wrap(s => s.length); +let f3: Mapper = arrayize(wrap(s => s.length)); +let f4: Mapper = combine(wrap(s => s.length), wrap(n => n >= 10)); + +foo(wrap(s => s.length)); + +let a1 = ["a", "b"].map(s => s.length); +let a2 = ["a", "b"].map(wrap(s => s.length)); +let a3 = ["a", "b"].map(wrap(arrayize(s => s.length))); +let a4 = ["a", "b"].map(combine(wrap(s => s.length), wrap(n => n > 10))); +let a5 = ["a", "b"].map(combine(identity, wrap(s => s.length))); +let a6 = ["a", "b"].map(combine(wrap(s => s.length), identity)); + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { + _store: A[]; + + add(a: A) { + this._store.push(a); + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { + return transformer(this); + } + + forEach(fn: (a: A, index: number) => void) { + this._store.forEach((a, i) => fn(a, i)); + } +} + +function compose( + fnA: (a: SetOf) => SetOf, + fnB: (b: SetOf) => SetOf, + fnC: (c: SetOf) => SetOf, + fnD: (c: SetOf) => SetOf, +):(x: SetOf) => SetOf; +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { + return (a: SetOf) => { + const b: SetOf = new SetOf(); + a.forEach(x => b.add(fn(x))); + return b; + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { + return (a: SetOf) => { + const result = new SetOf(); + a.forEach(x => { + if (predicate(x)) result.add(x); + }); + return result; + } +} + +const testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); + +const t1 = testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) + +declare function identity(x: T): T; + +const t2 = testSet.transform( + compose( + filter(x => x % 1 === 0), + identity, + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) From 5fa0fb46d181f8ad0895884f6d2a0698c868ef21 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 24 May 2017 15:50:39 -0700 Subject: [PATCH 12/56] Accept new baselines --- ...FromGenericFunctionReturnTypes1.errors.txt | 77 +++ .../inferFromGenericFunctionReturnTypes1.js | 123 ++++ .../inferFromGenericFunctionReturnTypes2.js | 155 +++++ ...ferFromGenericFunctionReturnTypes2.symbols | 480 ++++++++++++++ ...inferFromGenericFunctionReturnTypes2.types | 600 ++++++++++++++++++ 5 files changed, 1435 insertions(+) create mode 100644 tests/baselines/reference/inferFromGenericFunctionReturnTypes1.errors.txt create mode 100644 tests/baselines/reference/inferFromGenericFunctionReturnTypes1.js create mode 100644 tests/baselines/reference/inferFromGenericFunctionReturnTypes2.js create mode 100644 tests/baselines/reference/inferFromGenericFunctionReturnTypes2.symbols create mode 100644 tests/baselines/reference/inferFromGenericFunctionReturnTypes2.types diff --git a/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.errors.txt b/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.errors.txt new file mode 100644 index 00000000000..4ed8bdd81c6 --- /dev/null +++ b/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.errors.txt @@ -0,0 +1,77 @@ +tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts(68,16): error TS2339: Property 'toUpperCase' does not exist on type 'number'. + + +==== tests/cases/compiler/inferFromGenericFunctionReturnTypes1.ts (1 errors) ==== + // Repro from #15680 + + // This is a contrived class. We could do the same thing with Observables, etc. + class SetOf { + _store: A[]; + + add(a: A) { + this._store.push(a); + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { + return transformer(this); + } + + forEach(fn: (a: A, index: number) => void) { + this._store.forEach((a, i) => fn(a, i)); + } + } + + function compose( + fnA: (a: SetOf) => SetOf, + fnB: (b: SetOf) => SetOf, + fnC: (c: SetOf) => SetOf, + fnD: (c: SetOf) => SetOf, + ):(x: SetOf) => SetOf; + /* ... etc ... */ + function compose(...fns: ((x: T) => T)[]): (x: T) => T { + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); + } + + function map(fn: (a: A) => B): (s: SetOf) => SetOf { + return (a: SetOf) => { + const b: SetOf = new SetOf(); + a.forEach(x => b.add(fn(x))); + return b; + } + } + + function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { + return (a: SetOf) => { + const result = new SetOf(); + a.forEach(x => { + if (predicate(x)) result.add(x); + }); + return result; + } + } + + const testSet = new SetOf(); + testSet.add(1); + testSet.add(2); + testSet.add(3); + + testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) + ) + + testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => 123), // Whoops a bug + map(x => x.toUpperCase()) // causes an error! + ~~~~~~~~~~~ +!!! error TS2339: Property 'toUpperCase' does not exist on type 'number'. + ) + ) + \ No newline at end of file diff --git a/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.js b/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.js new file mode 100644 index 00000000000..0c3cf4b0cbe --- /dev/null +++ b/tests/baselines/reference/inferFromGenericFunctionReturnTypes1.js @@ -0,0 +1,123 @@ +//// [inferFromGenericFunctionReturnTypes1.ts] +// Repro from #15680 + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { + _store: A[]; + + add(a: A) { + this._store.push(a); + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { + return transformer(this); + } + + forEach(fn: (a: A, index: number) => void) { + this._store.forEach((a, i) => fn(a, i)); + } +} + +function compose( + fnA: (a: SetOf) => SetOf, + fnB: (b: SetOf) => SetOf, + fnC: (c: SetOf) => SetOf, + fnD: (c: SetOf) => SetOf, +):(x: SetOf) => SetOf; +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { + return (a: SetOf) => { + const b: SetOf = new SetOf(); + a.forEach(x => b.add(fn(x))); + return b; + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { + return (a: SetOf) => { + const result = new SetOf(); + a.forEach(x => { + if (predicate(x)) result.add(x); + }); + return result; + } +} + +const testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); + +testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) + +testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => 123), // Whoops a bug + map(x => x.toUpperCase()) // causes an error! + ) +) + + +//// [inferFromGenericFunctionReturnTypes1.js] +// Repro from #15680 +// This is a contrived class. We could do the same thing with Observables, etc. +var SetOf = (function () { + function SetOf() { + } + SetOf.prototype.add = function (a) { + this._store.push(a); + }; + SetOf.prototype.transform = function (transformer) { + return transformer(this); + }; + SetOf.prototype.forEach = function (fn) { + this._store.forEach(function (a, i) { return fn(a, i); }); + }; + return SetOf; +}()); +/* ... etc ... */ +function compose() { + var fns = []; + for (var _i = 0; _i < arguments.length; _i++) { + fns[_i] = arguments[_i]; + } + return function (x) { return fns.reduce(function (prev, fn) { return fn(prev); }, x); }; +} +function map(fn) { + return function (a) { + var b = new SetOf(); + a.forEach(function (x) { return b.add(fn(x)); }); + return b; + }; +} +function filter(predicate) { + return function (a) { + var result = new SetOf(); + a.forEach(function (x) { + if (predicate(x)) + result.add(x); + }); + return result; + }; +} +var testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); +testSet.transform(compose(filter(function (x) { return x % 1 === 0; }), map(function (x) { return x + x; }), map(function (x) { return x + '!!!'; }), map(function (x) { return x.toUpperCase(); }))); +testSet.transform(compose(filter(function (x) { return x % 1 === 0; }), map(function (x) { return x + x; }), map(function (x) { return 123; }), // Whoops a bug +map(function (x) { return x.toUpperCase(); }) // causes an error! +)); diff --git a/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.js b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.js new file mode 100644 index 00000000000..3f95b10d08a --- /dev/null +++ b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.js @@ -0,0 +1,155 @@ +//// [inferFromGenericFunctionReturnTypes2.ts] +type Mapper = (x: T) => U; + +declare function wrap(cb: Mapper): Mapper; + +declare function arrayize(cb: Mapper): Mapper; + +declare function combine(f: (x: A) => B, g: (x: B) => C): (x: A) => C; + +declare function foo(f: Mapper): void; + +let f1: Mapper = s => s.length; +let f2: Mapper = wrap(s => s.length); +let f3: Mapper = arrayize(wrap(s => s.length)); +let f4: Mapper = combine(wrap(s => s.length), wrap(n => n >= 10)); + +foo(wrap(s => s.length)); + +let a1 = ["a", "b"].map(s => s.length); +let a2 = ["a", "b"].map(wrap(s => s.length)); +let a3 = ["a", "b"].map(wrap(arrayize(s => s.length))); +let a4 = ["a", "b"].map(combine(wrap(s => s.length), wrap(n => n > 10))); +let a5 = ["a", "b"].map(combine(identity, wrap(s => s.length))); +let a6 = ["a", "b"].map(combine(wrap(s => s.length), identity)); + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { + _store: A[]; + + add(a: A) { + this._store.push(a); + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { + return transformer(this); + } + + forEach(fn: (a: A, index: number) => void) { + this._store.forEach((a, i) => fn(a, i)); + } +} + +function compose( + fnA: (a: SetOf) => SetOf, + fnB: (b: SetOf) => SetOf, + fnC: (c: SetOf) => SetOf, + fnD: (c: SetOf) => SetOf, +):(x: SetOf) => SetOf; +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { + return (a: SetOf) => { + const b: SetOf = new SetOf(); + a.forEach(x => b.add(fn(x))); + return b; + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { + return (a: SetOf) => { + const result = new SetOf(); + a.forEach(x => { + if (predicate(x)) result.add(x); + }); + return result; + } +} + +const testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); + +const t1 = testSet.transform( + compose( + filter(x => x % 1 === 0), + map(x => x + x), + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) + +declare function identity(x: T): T; + +const t2 = testSet.transform( + compose( + filter(x => x % 1 === 0), + identity, + map(x => x + '!!!'), + map(x => x.toUpperCase()) + ) +) + + +//// [inferFromGenericFunctionReturnTypes2.js] +var f1 = function (s) { return s.length; }; +var f2 = wrap(function (s) { return s.length; }); +var f3 = arrayize(wrap(function (s) { return s.length; })); +var f4 = combine(wrap(function (s) { return s.length; }), wrap(function (n) { return n >= 10; })); +foo(wrap(function (s) { return s.length; })); +var a1 = ["a", "b"].map(function (s) { return s.length; }); +var a2 = ["a", "b"].map(wrap(function (s) { return s.length; })); +var a3 = ["a", "b"].map(wrap(arrayize(function (s) { return s.length; }))); +var a4 = ["a", "b"].map(combine(wrap(function (s) { return s.length; }), wrap(function (n) { return n > 10; }))); +var a5 = ["a", "b"].map(combine(identity, wrap(function (s) { return s.length; }))); +var a6 = ["a", "b"].map(combine(wrap(function (s) { return s.length; }), identity)); +// This is a contrived class. We could do the same thing with Observables, etc. +var SetOf = (function () { + function SetOf() { + } + SetOf.prototype.add = function (a) { + this._store.push(a); + }; + SetOf.prototype.transform = function (transformer) { + return transformer(this); + }; + SetOf.prototype.forEach = function (fn) { + this._store.forEach(function (a, i) { return fn(a, i); }); + }; + return SetOf; +}()); +/* ... etc ... */ +function compose() { + var fns = []; + for (var _i = 0; _i < arguments.length; _i++) { + fns[_i] = arguments[_i]; + } + return function (x) { return fns.reduce(function (prev, fn) { return fn(prev); }, x); }; +} +function map(fn) { + return function (a) { + var b = new SetOf(); + a.forEach(function (x) { return b.add(fn(x)); }); + return b; + }; +} +function filter(predicate) { + return function (a) { + var result = new SetOf(); + a.forEach(function (x) { + if (predicate(x)) + result.add(x); + }); + return result; + }; +} +var testSet = new SetOf(); +testSet.add(1); +testSet.add(2); +testSet.add(3); +var t1 = testSet.transform(compose(filter(function (x) { return x % 1 === 0; }), map(function (x) { return x + x; }), map(function (x) { return x + '!!!'; }), map(function (x) { return x.toUpperCase(); }))); +var t2 = testSet.transform(compose(filter(function (x) { return x % 1 === 0; }), identity, map(function (x) { return x + '!!!'; }), map(function (x) { return x.toUpperCase(); }))); diff --git a/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.symbols b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.symbols new file mode 100644 index 00000000000..79a855badb5 --- /dev/null +++ b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.symbols @@ -0,0 +1,480 @@ +=== tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts === +type Mapper = (x: T) => U; +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 12)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 14)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 21)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 12)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 14)) + +declare function wrap(cb: Mapper): Mapper; +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 22)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 24)) +>cb : Symbol(cb, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 28)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 22)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 24)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 22)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 24)) + +declare function arrayize(cb: Mapper): Mapper; +>arrayize : Symbol(arrayize, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 60)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 26)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 28)) +>cb : Symbol(cb, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 32)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 26)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 28)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 26)) +>U : Symbol(U, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 28)) + +declare function combine(f: (x: A) => B, g: (x: B) => C): (x: A) => C; +>combine : Symbol(combine, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 66)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 25)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 27)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 30)) +>f : Symbol(f, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 34)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 38)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 25)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 27)) +>g : Symbol(g, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 49)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 54)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 27)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 30)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 68)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 25)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 30)) + +declare function foo(f: Mapper): void; +>foo : Symbol(foo, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 79)) +>f : Symbol(f, Decl(inferFromGenericFunctionReturnTypes2.ts, 8, 21)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) + +let f1: Mapper = s => s.length; +>f1 : Symbol(f1, Decl(inferFromGenericFunctionReturnTypes2.ts, 10, 3)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 10, 32)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 10, 32)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let f2: Mapper = wrap(s => s.length); +>f2 : Symbol(f2, Decl(inferFromGenericFunctionReturnTypes2.ts, 11, 3)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 11, 38)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 11, 38)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let f3: Mapper = arrayize(wrap(s => s.length)); +>f3 : Symbol(f3, Decl(inferFromGenericFunctionReturnTypes2.ts, 12, 3)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>arrayize : Symbol(arrayize, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 60)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 12, 49)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 12, 49)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let f4: Mapper = combine(wrap(s => s.length), wrap(n => n >= 10)); +>f4 : Symbol(f4, Decl(inferFromGenericFunctionReturnTypes2.ts, 13, 3)) +>Mapper : Symbol(Mapper, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 0)) +>combine : Symbol(combine, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 66)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 13, 47)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 13, 47)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>n : Symbol(n, Decl(inferFromGenericFunctionReturnTypes2.ts, 13, 68)) +>n : Symbol(n, Decl(inferFromGenericFunctionReturnTypes2.ts, 13, 68)) + +foo(wrap(s => s.length)); +>foo : Symbol(foo, Decl(inferFromGenericFunctionReturnTypes2.ts, 6, 79)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 15, 9)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 15, 9)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let a1 = ["a", "b"].map(s => s.length); +>a1 : Symbol(a1, Decl(inferFromGenericFunctionReturnTypes2.ts, 17, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 17, 24)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 17, 24)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let a2 = ["a", "b"].map(wrap(s => s.length)); +>a2 : Symbol(a2, Decl(inferFromGenericFunctionReturnTypes2.ts, 18, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 18, 29)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 18, 29)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let a3 = ["a", "b"].map(wrap(arrayize(s => s.length))); +>a3 : Symbol(a3, Decl(inferFromGenericFunctionReturnTypes2.ts, 19, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>arrayize : Symbol(arrayize, Decl(inferFromGenericFunctionReturnTypes2.ts, 2, 60)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 19, 38)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 19, 38)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let a4 = ["a", "b"].map(combine(wrap(s => s.length), wrap(n => n > 10))); +>a4 : Symbol(a4, Decl(inferFromGenericFunctionReturnTypes2.ts, 20, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>combine : Symbol(combine, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 66)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 20, 37)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 20, 37)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>n : Symbol(n, Decl(inferFromGenericFunctionReturnTypes2.ts, 20, 58)) +>n : Symbol(n, Decl(inferFromGenericFunctionReturnTypes2.ts, 20, 58)) + +let a5 = ["a", "b"].map(combine(identity, wrap(s => s.length))); +>a5 : Symbol(a5, Decl(inferFromGenericFunctionReturnTypes2.ts, 21, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>combine : Symbol(combine, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 66)) +>identity : Symbol(identity, Decl(inferFromGenericFunctionReturnTypes2.ts, 82, 1)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 21, 47)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 21, 47)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) + +let a6 = ["a", "b"].map(combine(wrap(s => s.length), identity)); +>a6 : Symbol(a6, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 3)) +>["a", "b"].map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>map : Symbol(Array.map, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>combine : Symbol(combine, Decl(inferFromGenericFunctionReturnTypes2.ts, 4, 66)) +>wrap : Symbol(wrap, Decl(inferFromGenericFunctionReturnTypes2.ts, 0, 32)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 37)) +>s.length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 37)) +>length : Symbol(String.length, Decl(lib.d.ts, --, --)) +>identity : Symbol(identity, Decl(inferFromGenericFunctionReturnTypes2.ts, 82, 1)) + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 12)) + + _store: A[]; +>_store : Symbol(SetOf._store, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 16)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 12)) + + add(a: A) { +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 28, 6)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 12)) + + this._store.push(a); +>this._store.push : Symbol(Array.push, Decl(lib.d.ts, --, --)) +>this._store : Symbol(SetOf._store, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 16)) +>this : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>_store : Symbol(SetOf._store, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 16)) +>push : Symbol(Array.push, Decl(lib.d.ts, --, --)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 28, 6)) + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { +>transform : Symbol(SetOf.transform, Decl(inferFromGenericFunctionReturnTypes2.ts, 30, 3)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 12)) +>transformer : Symbol(transformer, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 15)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 29)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 12)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 12)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 12)) + + return transformer(this); +>transformer : Symbol(transformer, Decl(inferFromGenericFunctionReturnTypes2.ts, 32, 15)) +>this : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) + } + + forEach(fn: (a: A, index: number) => void) { +>forEach : Symbol(SetOf.forEach, Decl(inferFromGenericFunctionReturnTypes2.ts, 34, 3)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 36, 10)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 36, 15)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 12)) +>index : Symbol(index, Decl(inferFromGenericFunctionReturnTypes2.ts, 36, 20)) + + this._store.forEach((a, i) => fn(a, i)); +>this._store.forEach : Symbol(Array.forEach, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>this._store : Symbol(SetOf._store, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 16)) +>this : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>_store : Symbol(SetOf._store, Decl(inferFromGenericFunctionReturnTypes2.ts, 25, 16)) +>forEach : Symbol(Array.forEach, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 37, 27)) +>i : Symbol(i, Decl(inferFromGenericFunctionReturnTypes2.ts, 37, 29)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 36, 10)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 37, 27)) +>i : Symbol(i, Decl(inferFromGenericFunctionReturnTypes2.ts, 37, 29)) + } +} + +function compose( +>compose : Symbol(compose, Decl(inferFromGenericFunctionReturnTypes2.ts, 39, 1), Decl(inferFromGenericFunctionReturnTypes2.ts, 46, 28)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 17)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 19)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 22)) +>D : Symbol(D, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 25)) +>E : Symbol(E, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 28)) + + fnA: (a: SetOf) => SetOf, +>fnA : Symbol(fnA, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 32)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 42, 8)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 17)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 19)) + + fnB: (b: SetOf) => SetOf, +>fnB : Symbol(fnB, Decl(inferFromGenericFunctionReturnTypes2.ts, 42, 33)) +>b : Symbol(b, Decl(inferFromGenericFunctionReturnTypes2.ts, 43, 8)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 19)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 22)) + + fnC: (c: SetOf) => SetOf, +>fnC : Symbol(fnC, Decl(inferFromGenericFunctionReturnTypes2.ts, 43, 33)) +>c : Symbol(c, Decl(inferFromGenericFunctionReturnTypes2.ts, 44, 8)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>C : Symbol(C, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 22)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>D : Symbol(D, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 25)) + + fnD: (c: SetOf) => SetOf, +>fnD : Symbol(fnD, Decl(inferFromGenericFunctionReturnTypes2.ts, 44, 33)) +>c : Symbol(c, Decl(inferFromGenericFunctionReturnTypes2.ts, 45, 8)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>D : Symbol(D, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 25)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>E : Symbol(E, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 28)) + +):(x: SetOf) => SetOf; +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 46, 3)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 17)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>E : Symbol(E, Decl(inferFromGenericFunctionReturnTypes2.ts, 41, 28)) + +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { +>compose : Symbol(compose, Decl(inferFromGenericFunctionReturnTypes2.ts, 39, 1), Decl(inferFromGenericFunctionReturnTypes2.ts, 46, 28)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) +>fns : Symbol(fns, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 20)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 30)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 47)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) + + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 10)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 17)) +>fns.reduce : Symbol(Array.reduce, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>fns : Symbol(fns, Decl(inferFromGenericFunctionReturnTypes2.ts, 48, 20)) +>reduce : Symbol(Array.reduce, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) +>prev : Symbol(prev, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 31)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 36)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 36)) +>prev : Symbol(prev, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 31)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 49, 10)) +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 13)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 15)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 19)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 24)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 13)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 15)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 38)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 13)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 15)) + + return (a: SetOf) => { +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 53, 10)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 13)) + + const b: SetOf = new SetOf(); +>b : Symbol(b, Decl(inferFromGenericFunctionReturnTypes2.ts, 54, 9)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>B : Symbol(B, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 15)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) + + a.forEach(x => b.add(fn(x))); +>a.forEach : Symbol(SetOf.forEach, Decl(inferFromGenericFunctionReturnTypes2.ts, 34, 3)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 53, 10)) +>forEach : Symbol(SetOf.forEach, Decl(inferFromGenericFunctionReturnTypes2.ts, 34, 3)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 55, 14)) +>b.add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>b : Symbol(b, Decl(inferFromGenericFunctionReturnTypes2.ts, 54, 9)) +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>fn : Symbol(fn, Decl(inferFromGenericFunctionReturnTypes2.ts, 52, 19)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 55, 14)) + + return b; +>b : Symbol(b, Decl(inferFromGenericFunctionReturnTypes2.ts, 54, 9)) + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { +>filter : Symbol(filter, Decl(inferFromGenericFunctionReturnTypes2.ts, 58, 1)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) +>predicate : Symbol(predicate, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 19)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 31)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) +>s : Symbol(s, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 51)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) + + return (a: SetOf) => { +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 61, 10)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) + + const result = new SetOf(); +>result : Symbol(result, Decl(inferFromGenericFunctionReturnTypes2.ts, 62, 9)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) +>A : Symbol(A, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 16)) + + a.forEach(x => { +>a.forEach : Symbol(SetOf.forEach, Decl(inferFromGenericFunctionReturnTypes2.ts, 34, 3)) +>a : Symbol(a, Decl(inferFromGenericFunctionReturnTypes2.ts, 61, 10)) +>forEach : Symbol(SetOf.forEach, Decl(inferFromGenericFunctionReturnTypes2.ts, 34, 3)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 63, 14)) + + if (predicate(x)) result.add(x); +>predicate : Symbol(predicate, Decl(inferFromGenericFunctionReturnTypes2.ts, 60, 19)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 63, 14)) +>result.add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>result : Symbol(result, Decl(inferFromGenericFunctionReturnTypes2.ts, 62, 9)) +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 63, 14)) + + }); + return result; +>result : Symbol(result, Decl(inferFromGenericFunctionReturnTypes2.ts, 62, 9)) + } +} + +const testSet = new SetOf(); +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>SetOf : Symbol(SetOf, Decl(inferFromGenericFunctionReturnTypes2.ts, 22, 64)) + +testSet.add(1); +>testSet.add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) + +testSet.add(2); +>testSet.add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) + +testSet.add(3); +>testSet.add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>add : Symbol(SetOf.add, Decl(inferFromGenericFunctionReturnTypes2.ts, 26, 14)) + +const t1 = testSet.transform( +>t1 : Symbol(t1, Decl(inferFromGenericFunctionReturnTypes2.ts, 75, 5)) +>testSet.transform : Symbol(SetOf.transform, Decl(inferFromGenericFunctionReturnTypes2.ts, 30, 3)) +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>transform : Symbol(SetOf.transform, Decl(inferFromGenericFunctionReturnTypes2.ts, 30, 3)) + + compose( +>compose : Symbol(compose, Decl(inferFromGenericFunctionReturnTypes2.ts, 39, 1), Decl(inferFromGenericFunctionReturnTypes2.ts, 46, 28)) + + filter(x => x % 1 === 0), +>filter : Symbol(filter, Decl(inferFromGenericFunctionReturnTypes2.ts, 58, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 77, 11)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 77, 11)) + + map(x => x + x), +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 78, 8)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 78, 8)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 78, 8)) + + map(x => x + '!!!'), +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 79, 8)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 79, 8)) + + map(x => x.toUpperCase()) +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 80, 8)) +>x.toUpperCase : Symbol(String.toUpperCase, Decl(lib.d.ts, --, --)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 80, 8)) +>toUpperCase : Symbol(String.toUpperCase, Decl(lib.d.ts, --, --)) + + ) +) + +declare function identity(x: T): T; +>identity : Symbol(identity, Decl(inferFromGenericFunctionReturnTypes2.ts, 82, 1)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 84, 26)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 84, 29)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 84, 26)) +>T : Symbol(T, Decl(inferFromGenericFunctionReturnTypes2.ts, 84, 26)) + +const t2 = testSet.transform( +>t2 : Symbol(t2, Decl(inferFromGenericFunctionReturnTypes2.ts, 86, 5)) +>testSet.transform : Symbol(SetOf.transform, Decl(inferFromGenericFunctionReturnTypes2.ts, 30, 3)) +>testSet : Symbol(testSet, Decl(inferFromGenericFunctionReturnTypes2.ts, 70, 5)) +>transform : Symbol(SetOf.transform, Decl(inferFromGenericFunctionReturnTypes2.ts, 30, 3)) + + compose( +>compose : Symbol(compose, Decl(inferFromGenericFunctionReturnTypes2.ts, 39, 1), Decl(inferFromGenericFunctionReturnTypes2.ts, 46, 28)) + + filter(x => x % 1 === 0), +>filter : Symbol(filter, Decl(inferFromGenericFunctionReturnTypes2.ts, 58, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 88, 11)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 88, 11)) + + identity, +>identity : Symbol(identity, Decl(inferFromGenericFunctionReturnTypes2.ts, 82, 1)) + + map(x => x + '!!!'), +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 90, 8)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 90, 8)) + + map(x => x.toUpperCase()) +>map : Symbol(map, Decl(inferFromGenericFunctionReturnTypes2.ts, 50, 1)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 91, 8)) +>x.toUpperCase : Symbol(String.toUpperCase, Decl(lib.d.ts, --, --)) +>x : Symbol(x, Decl(inferFromGenericFunctionReturnTypes2.ts, 91, 8)) +>toUpperCase : Symbol(String.toUpperCase, Decl(lib.d.ts, --, --)) + + ) +) + diff --git a/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.types b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.types new file mode 100644 index 00000000000..a07c5ea4db8 --- /dev/null +++ b/tests/baselines/reference/inferFromGenericFunctionReturnTypes2.types @@ -0,0 +1,600 @@ +=== tests/cases/compiler/inferFromGenericFunctionReturnTypes2.ts === +type Mapper = (x: T) => U; +>Mapper : Mapper +>T : T +>U : U +>x : T +>T : T +>U : U + +declare function wrap(cb: Mapper): Mapper; +>wrap : (cb: Mapper) => Mapper +>T : T +>U : U +>cb : Mapper +>Mapper : Mapper +>T : T +>U : U +>Mapper : Mapper +>T : T +>U : U + +declare function arrayize(cb: Mapper): Mapper; +>arrayize : (cb: Mapper) => Mapper +>T : T +>U : U +>cb : Mapper +>Mapper : Mapper +>T : T +>U : U +>Mapper : Mapper +>T : T +>U : U + +declare function combine(f: (x: A) => B, g: (x: B) => C): (x: A) => C; +>combine : (f: (x: A) => B, g: (x: B) => C) => (x: A) => C +>A : A +>B : B +>C : C +>f : (x: A) => B +>x : A +>A : A +>B : B +>g : (x: B) => C +>x : B +>B : B +>C : C +>x : A +>A : A +>C : C + +declare function foo(f: Mapper): void; +>foo : (f: Mapper) => void +>f : Mapper +>Mapper : Mapper + +let f1: Mapper = s => s.length; +>f1 : Mapper +>Mapper : Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let f2: Mapper = wrap(s => s.length); +>f2 : Mapper +>Mapper : Mapper +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let f3: Mapper = arrayize(wrap(s => s.length)); +>f3 : Mapper +>Mapper : Mapper +>arrayize(wrap(s => s.length)) : Mapper +>arrayize : (cb: Mapper) => Mapper +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let f4: Mapper = combine(wrap(s => s.length), wrap(n => n >= 10)); +>f4 : Mapper +>Mapper : Mapper +>combine(wrap(s => s.length), wrap(n => n >= 10)) : (x: string) => boolean +>combine : (f: (x: A) => B, g: (x: B) => C) => (x: A) => C +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number +>wrap(n => n >= 10) : Mapper +>wrap : (cb: Mapper) => Mapper +>n => n >= 10 : (n: number) => boolean +>n : number +>n >= 10 : boolean +>n : number +>10 : 10 + +foo(wrap(s => s.length)); +>foo(wrap(s => s.length)) : void +>foo : (f: Mapper) => void +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let a1 = ["a", "b"].map(s => s.length); +>a1 : number[] +>["a", "b"].map(s => s.length) : number[] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>s => s.length : (this: void, s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let a2 = ["a", "b"].map(wrap(s => s.length)); +>a2 : number[] +>["a", "b"].map(wrap(s => s.length)) : number[] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let a3 = ["a", "b"].map(wrap(arrayize(s => s.length))); +>a3 : number[][] +>["a", "b"].map(wrap(arrayize(s => s.length))) : number[][] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>wrap(arrayize(s => s.length)) : Mapper +>wrap : (cb: Mapper) => Mapper +>arrayize(s => s.length) : Mapper +>arrayize : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let a4 = ["a", "b"].map(combine(wrap(s => s.length), wrap(n => n > 10))); +>a4 : boolean[] +>["a", "b"].map(combine(wrap(s => s.length), wrap(n => n > 10))) : boolean[] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>combine(wrap(s => s.length), wrap(n => n > 10)) : (x: string) => boolean +>combine : (f: (x: A) => B, g: (x: B) => C) => (x: A) => C +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number +>wrap(n => n > 10) : Mapper +>wrap : (cb: Mapper) => Mapper +>n => n > 10 : (n: number) => boolean +>n : number +>n > 10 : boolean +>n : number +>10 : 10 + +let a5 = ["a", "b"].map(combine(identity, wrap(s => s.length))); +>a5 : number[] +>["a", "b"].map(combine(identity, wrap(s => s.length))) : number[] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>combine(identity, wrap(s => s.length)) : (x: string) => number +>combine : (f: (x: A) => B, g: (x: B) => C) => (x: A) => C +>identity : (x: T) => T +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number + +let a6 = ["a", "b"].map(combine(wrap(s => s.length), identity)); +>a6 : number[] +>["a", "b"].map(combine(wrap(s => s.length), identity)) : number[] +>["a", "b"].map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>["a", "b"] : string[] +>"a" : "a" +>"b" : "b" +>map : { (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U, U]; (this: [string, string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U, U]; (this: [string, string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U, U]; (this: [string, string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U, U]; (this: [string, string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U): [U, U]; (this: [string, string], callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): [U, U]; (this: [string, string], callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): [U, U]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U): U[]; (callbackfn: (this: void, value: string, index: number, array: string[]) => U, thisArg: undefined): U[]; (callbackfn: (this: Z, value: string, index: number, array: string[]) => U, thisArg: Z): U[]; } +>combine(wrap(s => s.length), identity) : (x: string) => number +>combine : (f: (x: A) => B, g: (x: B) => C) => (x: A) => C +>wrap(s => s.length) : Mapper +>wrap : (cb: Mapper) => Mapper +>s => s.length : (s: string) => number +>s : string +>s.length : number +>s : string +>length : number +>identity : (x: T) => T + +// This is a contrived class. We could do the same thing with Observables, etc. +class SetOf { +>SetOf : SetOf +>A : A + + _store: A[]; +>_store : A[] +>A : A + + add(a: A) { +>add : (a: A) => void +>a : A +>A : A + + this._store.push(a); +>this._store.push(a) : number +>this._store.push : (...items: A[]) => number +>this._store : A[] +>this : this +>_store : A[] +>push : (...items: A[]) => number +>a : A + } + + transform(transformer: (a: SetOf) => SetOf): SetOf { +>transform : (transformer: (a: SetOf) => SetOf) => SetOf +>B : B +>transformer : (a: SetOf) => SetOf +>a : SetOf +>SetOf : SetOf +>A : A +>SetOf : SetOf +>B : B +>SetOf : SetOf +>B : B + + return transformer(this); +>transformer(this) : SetOf +>transformer : (a: SetOf) => SetOf +>this : this + } + + forEach(fn: (a: A, index: number) => void) { +>forEach : (fn: (a: A, index: number) => void) => void +>fn : (a: A, index: number) => void +>a : A +>A : A +>index : number + + this._store.forEach((a, i) => fn(a, i)); +>this._store.forEach((a, i) => fn(a, i)) : void +>this._store.forEach : { (callbackfn: (this: void, value: A, index: number, array: A[]) => void): void; (callbackfn: (this: void, value: A, index: number, array: A[]) => void, thisArg: undefined): void; (callbackfn: (this: Z, value: A, index: number, array: A[]) => void, thisArg: Z): void; } +>this._store : A[] +>this : this +>_store : A[] +>forEach : { (callbackfn: (this: void, value: A, index: number, array: A[]) => void): void; (callbackfn: (this: void, value: A, index: number, array: A[]) => void, thisArg: undefined): void; (callbackfn: (this: Z, value: A, index: number, array: A[]) => void, thisArg: Z): void; } +>(a, i) => fn(a, i) : (this: void, a: A, i: number) => void +>a : A +>i : number +>fn(a, i) : void +>fn : (a: A, index: number) => void +>a : A +>i : number + } +} + +function compose( +>compose : (fnA: (a: SetOf) => SetOf, fnB: (b: SetOf) => SetOf, fnC: (c: SetOf) => SetOf, fnD: (c: SetOf) => SetOf) => (x: SetOf) => SetOf +>A : A +>B : B +>C : C +>D : D +>E : E + + fnA: (a: SetOf) => SetOf, +>fnA : (a: SetOf) => SetOf +>a : SetOf +>SetOf : SetOf +>A : A +>SetOf : SetOf +>B : B + + fnB: (b: SetOf) => SetOf, +>fnB : (b: SetOf) => SetOf +>b : SetOf +>SetOf : SetOf +>B : B +>SetOf : SetOf +>C : C + + fnC: (c: SetOf) => SetOf, +>fnC : (c: SetOf) => SetOf +>c : SetOf +>SetOf : SetOf +>C : C +>SetOf : SetOf +>D : D + + fnD: (c: SetOf) => SetOf, +>fnD : (c: SetOf) => SetOf +>c : SetOf +>SetOf : SetOf +>D : D +>SetOf : SetOf +>E : E + +):(x: SetOf) => SetOf; +>x : SetOf +>SetOf : SetOf +>A : A +>SetOf : SetOf +>E : E + +/* ... etc ... */ +function compose(...fns: ((x: T) => T)[]): (x: T) => T { +>compose : (fnA: (a: SetOf) => SetOf, fnB: (b: SetOf) => SetOf, fnC: (c: SetOf) => SetOf, fnD: (c: SetOf) => SetOf) => (x: SetOf) => SetOf +>T : T +>fns : ((x: T) => T)[] +>x : T +>T : T +>T : T +>x : T +>T : T +>T : T + + return (x: T) => fns.reduce((prev, fn) => fn(prev), x); +>(x: T) => fns.reduce((prev, fn) => fn(prev), x) : (x: T) => T +>x : T +>T : T +>fns.reduce((prev, fn) => fn(prev), x) : T +>fns.reduce : { (callbackfn: (previousValue: (x: T) => T, currentValue: (x: T) => T, currentIndex: number, array: ((x: T) => T)[]) => (x: T) => T, initialValue?: (x: T) => T): (x: T) => T; (callbackfn: (previousValue: U, currentValue: (x: T) => T, currentIndex: number, array: ((x: T) => T)[]) => U, initialValue: U): U; } +>fns : ((x: T) => T)[] +>reduce : { (callbackfn: (previousValue: (x: T) => T, currentValue: (x: T) => T, currentIndex: number, array: ((x: T) => T)[]) => (x: T) => T, initialValue?: (x: T) => T): (x: T) => T; (callbackfn: (previousValue: U, currentValue: (x: T) => T, currentIndex: number, array: ((x: T) => T)[]) => U, initialValue: U): U; } +>(prev, fn) => fn(prev) : (prev: T, fn: (x: T) => T) => T +>prev : T +>fn : (x: T) => T +>fn(prev) : T +>fn : (x: T) => T +>prev : T +>x : T +} + +function map(fn: (a: A) => B): (s: SetOf) => SetOf { +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>A : A +>B : B +>fn : (a: A) => B +>a : A +>A : A +>B : B +>s : SetOf +>SetOf : SetOf +>A : A +>SetOf : SetOf +>B : B + + return (a: SetOf) => { +>(a: SetOf) => { const b: SetOf = new SetOf(); a.forEach(x => b.add(fn(x))); return b; } : (a: SetOf) => SetOf +>a : SetOf +>SetOf : SetOf +>A : A + + const b: SetOf = new SetOf(); +>b : SetOf +>SetOf : SetOf +>B : B +>new SetOf() : SetOf +>SetOf : typeof SetOf + + a.forEach(x => b.add(fn(x))); +>a.forEach(x => b.add(fn(x))) : void +>a.forEach : (fn: (a: A, index: number) => void) => void +>a : SetOf +>forEach : (fn: (a: A, index: number) => void) => void +>x => b.add(fn(x)) : (x: A) => void +>x : A +>b.add(fn(x)) : void +>b.add : (a: B) => void +>b : SetOf +>add : (a: B) => void +>fn(x) : B +>fn : (a: A) => B +>x : A + + return b; +>b : SetOf + } +} + +function filter(predicate: (a: A) => boolean): (s: SetOf) => SetOf { +>filter : (predicate: (a: A) => boolean) => (s: SetOf) => SetOf +>A : A +>predicate : (a: A) => boolean +>a : A +>A : A +>s : SetOf +>SetOf : SetOf +>A : A +>SetOf : SetOf +>A : A + + return (a: SetOf) => { +>(a: SetOf) => { const result = new SetOf(); a.forEach(x => { if (predicate(x)) result.add(x); }); return result; } : (a: SetOf) => SetOf +>a : SetOf +>SetOf : SetOf +>A : A + + const result = new SetOf(); +>result : SetOf +>new SetOf() : SetOf +>SetOf : typeof SetOf +>A : A + + a.forEach(x => { +>a.forEach(x => { if (predicate(x)) result.add(x); }) : void +>a.forEach : (fn: (a: A, index: number) => void) => void +>a : SetOf +>forEach : (fn: (a: A, index: number) => void) => void +>x => { if (predicate(x)) result.add(x); } : (x: A) => void +>x : A + + if (predicate(x)) result.add(x); +>predicate(x) : boolean +>predicate : (a: A) => boolean +>x : A +>result.add(x) : void +>result.add : (a: A) => void +>result : SetOf +>add : (a: A) => void +>x : A + + }); + return result; +>result : SetOf + } +} + +const testSet = new SetOf(); +>testSet : SetOf +>new SetOf() : SetOf +>SetOf : typeof SetOf + +testSet.add(1); +>testSet.add(1) : void +>testSet.add : (a: number) => void +>testSet : SetOf +>add : (a: number) => void +>1 : 1 + +testSet.add(2); +>testSet.add(2) : void +>testSet.add : (a: number) => void +>testSet : SetOf +>add : (a: number) => void +>2 : 2 + +testSet.add(3); +>testSet.add(3) : void +>testSet.add : (a: number) => void +>testSet : SetOf +>add : (a: number) => void +>3 : 3 + +const t1 = testSet.transform( +>t1 : SetOf +>testSet.transform( compose( filter(x => x % 1 === 0), map(x => x + x), map(x => x + '!!!'), map(x => x.toUpperCase()) )) : SetOf +>testSet.transform : (transformer: (a: SetOf) => SetOf) => SetOf +>testSet : SetOf +>transform : (transformer: (a: SetOf) => SetOf) => SetOf + + compose( +>compose( filter(x => x % 1 === 0), map(x => x + x), map(x => x + '!!!'), map(x => x.toUpperCase()) ) : (x: SetOf) => SetOf +>compose : (fnA: (a: SetOf) => SetOf, fnB: (b: SetOf) => SetOf, fnC: (c: SetOf) => SetOf, fnD: (c: SetOf) => SetOf) => (x: SetOf) => SetOf + + filter(x => x % 1 === 0), +>filter(x => x % 1 === 0) : (s: SetOf) => SetOf +>filter : (predicate: (a: A) => boolean) => (s: SetOf) => SetOf +>x => x % 1 === 0 : (x: number) => boolean +>x : number +>x % 1 === 0 : boolean +>x % 1 : number +>x : number +>1 : 1 +>0 : 0 + + map(x => x + x), +>map(x => x + x) : (s: SetOf) => SetOf +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>x => x + x : (x: number) => number +>x : number +>x + x : number +>x : number +>x : number + + map(x => x + '!!!'), +>map(x => x + '!!!') : (s: SetOf) => SetOf +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>x => x + '!!!' : (x: number) => string +>x : number +>x + '!!!' : string +>x : number +>'!!!' : "!!!" + + map(x => x.toUpperCase()) +>map(x => x.toUpperCase()) : (s: SetOf) => SetOf +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>x => x.toUpperCase() : (x: string) => string +>x : string +>x.toUpperCase() : string +>x.toUpperCase : () => string +>x : string +>toUpperCase : () => string + + ) +) + +declare function identity(x: T): T; +>identity : (x: T) => T +>T : T +>x : T +>T : T +>T : T + +const t2 = testSet.transform( +>t2 : SetOf +>testSet.transform( compose( filter(x => x % 1 === 0), identity, map(x => x + '!!!'), map(x => x.toUpperCase()) )) : SetOf +>testSet.transform : (transformer: (a: SetOf) => SetOf) => SetOf +>testSet : SetOf +>transform : (transformer: (a: SetOf) => SetOf) => SetOf + + compose( +>compose( filter(x => x % 1 === 0), identity, map(x => x + '!!!'), map(x => x.toUpperCase()) ) : (x: SetOf) => SetOf +>compose : (fnA: (a: SetOf) => SetOf, fnB: (b: SetOf) => SetOf, fnC: (c: SetOf) => SetOf, fnD: (c: SetOf) => SetOf) => (x: SetOf) => SetOf + + filter(x => x % 1 === 0), +>filter(x => x % 1 === 0) : (s: SetOf) => SetOf +>filter : (predicate: (a: A) => boolean) => (s: SetOf) => SetOf +>x => x % 1 === 0 : (x: number) => boolean +>x : number +>x % 1 === 0 : boolean +>x % 1 : number +>x : number +>1 : 1 +>0 : 0 + + identity, +>identity : (x: T) => T + + map(x => x + '!!!'), +>map(x => x + '!!!') : (s: SetOf) => SetOf +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>x => x + '!!!' : (x: number) => string +>x : number +>x + '!!!' : string +>x : number +>'!!!' : "!!!" + + map(x => x.toUpperCase()) +>map(x => x.toUpperCase()) : (s: SetOf) => SetOf +>map : (fn: (a: A) => B) => (s: SetOf) => SetOf +>x => x.toUpperCase() : (x: string) => string +>x : string +>x.toUpperCase() : string +>x.toUpperCase : () => string +>x : string +>toUpperCase : () => string + + ) +) + From 348fc7e51e1df2136b815c7d2847ede78983bccc Mon Sep 17 00:00:00 2001 From: Kanchalai Tanglertsampan Date: Wed, 24 May 2017 16:37:02 -0700 Subject: [PATCH 13/56] Take into account optional property in parameter --- src/compiler/binder.ts | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/compiler/binder.ts b/src/compiler/binder.ts index 204a979d928..8870757999f 100644 --- a/src/compiler/binder.ts +++ b/src/compiler/binder.ts @@ -1,4 +1,4 @@ -/// +/// /// /* @internal */ @@ -2178,7 +2178,11 @@ namespace ts { case SyntaxKind.JSDocRecordMember: return bindPropertyWorker(node as JSDocRecordMember); case SyntaxKind.JSDocPropertyTag: - return declareSymbolAndAddToSymbolTable(node as JSDocPropertyTag, SymbolFlags.Property, SymbolFlags.PropertyExcludes); + let optionalType = 0; + if ((node as JSDocPropertyTag).typeExpression.type.kind === SyntaxKind.JSDocOptionalType) { + optionalType = SymbolFlags.Optional; + } + return declareSymbolAndAddToSymbolTable(node as JSDocPropertyTag, SymbolFlags.Property | optionalType, SymbolFlags.PropertyExcludes); case SyntaxKind.JSDocFunctionType: return bindFunctionOrConstructorType(node); case SyntaxKind.JSDocTypeLiteral: From 0d1e41d9379f32d33b8751d079cb7255ef302e78 Mon Sep 17 00:00:00 2001 From: Andy Hanson Date: Thu, 25 May 2017 08:40:27 -0700 Subject: [PATCH 14/56] In findAllReferences, always return undefined (global) symbol scope for properties; also update baselines --- src/services/findAllReferences.ts | 9 +++------ .../isomorphicMappedTypeInference.symbols | 4 ++-- .../reference/keyofAndIndexedAccess.symbols | 16 +++++++-------- .../reference/mappedTypeModifiers.symbols | 16 +++++++-------- .../baselines/reference/mappedTypes2.symbols | 20 +++++++++---------- .../baselines/reference/mappedTypes3.symbols | 8 ++++---- .../reference/typeVariableTypeGuards.symbols | 8 ++++---- 7 files changed, 39 insertions(+), 42 deletions(-) diff --git a/src/services/findAllReferences.ts b/src/services/findAllReferences.ts index efc6a6f6ed1..e12215abde0 100644 --- a/src/services/findAllReferences.ts +++ b/src/services/findAllReferences.ts @@ -650,10 +650,12 @@ namespace ts.FindAllReferences.Core { // If this is private property or method, the scope is the containing class if (flags & (SymbolFlags.Property | SymbolFlags.Method)) { - const privateDeclaration = find(declarations, d => !!(getModifierFlags(d) & ModifierFlags.Private)); + const privateDeclaration = find(declarations, d => hasModifier(d, ModifierFlags.Private)); if (privateDeclaration) { return getAncestor(privateDeclaration, SyntaxKind.ClassDeclaration); } + // Else this is a public property and could be accessed from anywhere. + return undefined; } // If symbol is of object binding pattern element without property name we would want to @@ -669,11 +671,6 @@ namespace ts.FindAllReferences.Core { return undefined; } - // If this is a synthetic property, it's a property and must be searched for globally. - if ((flags & SymbolFlags.Transient && (symbol).checkFlags & CheckFlags.Synthetic)) { - return undefined; - } - let scope: Node | undefined; for (const declaration of declarations) { const container = getContainerNode(declaration); diff --git a/tests/baselines/reference/isomorphicMappedTypeInference.symbols b/tests/baselines/reference/isomorphicMappedTypeInference.symbols index 6c638f442c8..48765d15260 100644 --- a/tests/baselines/reference/isomorphicMappedTypeInference.symbols +++ b/tests/baselines/reference/isomorphicMappedTypeInference.symbols @@ -149,9 +149,9 @@ function f1() { let x: number = b.a.value; >x : Symbol(x, Decl(isomorphicMappedTypeInference.ts, 45, 7)) >b.a.value : Symbol(value, Decl(isomorphicMappedTypeInference.ts, 0, 15)) ->b.a : Symbol(a) +>b.a : Symbol(a, Decl(isomorphicMappedTypeInference.ts, 39, 13)) >b : Symbol(b, Decl(isomorphicMappedTypeInference.ts, 44, 7)) ->a : Symbol(a) +>a : Symbol(a, Decl(isomorphicMappedTypeInference.ts, 39, 13)) >value : Symbol(value, Decl(isomorphicMappedTypeInference.ts, 0, 15)) } diff --git a/tests/baselines/reference/keyofAndIndexedAccess.symbols b/tests/baselines/reference/keyofAndIndexedAccess.symbols index 6d7e886d26c..65cc44fe84b 100644 --- a/tests/baselines/reference/keyofAndIndexedAccess.symbols +++ b/tests/baselines/reference/keyofAndIndexedAccess.symbols @@ -820,19 +820,19 @@ function f71(func: (x: T, y: U) => Partial) { >c : Symbol(c, Decl(keyofAndIndexedAccess.ts, 226, 40)) x.a; // number | undefined ->x.a : Symbol(a) +>x.a : Symbol(a, Decl(keyofAndIndexedAccess.ts, 226, 18)) >x : Symbol(x, Decl(keyofAndIndexedAccess.ts, 226, 7)) ->a : Symbol(a) +>a : Symbol(a, Decl(keyofAndIndexedAccess.ts, 226, 18)) x.b; // string | undefined ->x.b : Symbol(b) +>x.b : Symbol(b, Decl(keyofAndIndexedAccess.ts, 226, 24)) >x : Symbol(x, Decl(keyofAndIndexedAccess.ts, 226, 7)) ->b : Symbol(b) +>b : Symbol(b, Decl(keyofAndIndexedAccess.ts, 226, 24)) x.c; // boolean | undefined ->x.c : Symbol(c) +>x.c : Symbol(c, Decl(keyofAndIndexedAccess.ts, 226, 40)) >x : Symbol(x, Decl(keyofAndIndexedAccess.ts, 226, 7)) ->c : Symbol(c) +>c : Symbol(c, Decl(keyofAndIndexedAccess.ts, 226, 40)) } function f72(func: (x: T, y: U, k: K) => (T & U)[K]) { @@ -1951,11 +1951,11 @@ class AnotherSampleClass extends SampleClass { this.props.foo.concat; >this.props.foo.concat : Symbol(String.concat, Decl(lib.d.ts, --, --)) ->this.props.foo : Symbol(foo) +>this.props.foo : Symbol(foo, Decl(keyofAndIndexedAccess.ts, 536, 15)) >this.props : Symbol(SampleClass.props, Decl(keyofAndIndexedAccess.ts, 529, 22)) >this : Symbol(AnotherSampleClass, Decl(keyofAndIndexedAccess.ts, 540, 54)) >props : Symbol(SampleClass.props, Decl(keyofAndIndexedAccess.ts, 529, 22)) ->foo : Symbol(foo) +>foo : Symbol(foo, Decl(keyofAndIndexedAccess.ts, 536, 15)) >concat : Symbol(String.concat, Decl(lib.d.ts, --, --)) } } diff --git a/tests/baselines/reference/mappedTypeModifiers.symbols b/tests/baselines/reference/mappedTypeModifiers.symbols index 2aa6492d99f..363345a2e55 100644 --- a/tests/baselines/reference/mappedTypeModifiers.symbols +++ b/tests/baselines/reference/mappedTypeModifiers.symbols @@ -364,9 +364,9 @@ function f1(x: Partial) { >Foo : Symbol(Foo, Decl(mappedTypeModifiers.ts, 74, 30)) x.prop; // ok ->x.prop : Symbol(prop) +>x.prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) >x : Symbol(x, Decl(mappedTypeModifiers.ts, 78, 12)) ->prop : Symbol(prop) +>prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) (x["other"] || 0).toFixed(); >(x["other"] || 0).toFixed : Symbol(Number.toFixed, Decl(lib.d.ts, --, --)) @@ -381,9 +381,9 @@ function f2(x: Readonly) { >Foo : Symbol(Foo, Decl(mappedTypeModifiers.ts, 74, 30)) x.prop; // ok ->x.prop : Symbol(prop) +>x.prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) >x : Symbol(x, Decl(mappedTypeModifiers.ts, 83, 12)) ->prop : Symbol(prop) +>prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) x["other"].toFixed(); >x["other"].toFixed : Symbol(Number.toFixed, Decl(lib.d.ts, --, --)) @@ -398,9 +398,9 @@ function f3(x: Boxified) { >Foo : Symbol(Foo, Decl(mappedTypeModifiers.ts, 74, 30)) x.prop; // ok ->x.prop : Symbol(prop) +>x.prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) >x : Symbol(x, Decl(mappedTypeModifiers.ts, 88, 12)) ->prop : Symbol(prop) +>prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) x["other"].x.toFixed(); >x["other"].x.toFixed : Symbol(Number.toFixed, Decl(lib.d.ts, --, --)) @@ -419,9 +419,9 @@ function f4(x: { [P in keyof Foo]: Foo[P] }) { >P : Symbol(P, Decl(mappedTypeModifiers.ts, 93, 18)) x.prop; // ok ->x.prop : Symbol(prop) +>x.prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) >x : Symbol(x, Decl(mappedTypeModifiers.ts, 93, 12)) ->prop : Symbol(prop) +>prop : Symbol(prop, Decl(mappedTypeModifiers.ts, 76, 12)) x["other"].toFixed(); >x["other"].toFixed : Symbol(Number.toFixed, Decl(lib.d.ts, --, --)) diff --git a/tests/baselines/reference/mappedTypes2.symbols b/tests/baselines/reference/mappedTypes2.symbols index 7d9727daedd..9100c408ee9 100644 --- a/tests/baselines/reference/mappedTypes2.symbols +++ b/tests/baselines/reference/mappedTypes2.symbols @@ -313,16 +313,16 @@ function f5(shape: Shape) { let name = p.name.get(); >name : Symbol(name, Decl(mappedTypes2.ts, 84, 7)) >p.name.get : Symbol(get, Decl(mappedTypes2.ts, 11, 17)) ->p.name : Symbol(name) +>p.name : Symbol(name, Decl(mappedTypes2.ts, 35, 17)) >p : Symbol(p, Decl(mappedTypes2.ts, 83, 9)) ->name : Symbol(name) +>name : Symbol(name, Decl(mappedTypes2.ts, 35, 17)) >get : Symbol(get, Decl(mappedTypes2.ts, 11, 17)) p.width.set(42); >p.width.set : Symbol(set, Decl(mappedTypes2.ts, 12, 13)) ->p.width : Symbol(width) +>p.width : Symbol(width, Decl(mappedTypes2.ts, 36, 17)) >p : Symbol(p, Decl(mappedTypes2.ts, 83, 9)) ->width : Symbol(width) +>width : Symbol(width, Decl(mappedTypes2.ts, 36, 17)) >set : Symbol(set, Decl(mappedTypes2.ts, 12, 13)) } @@ -334,19 +334,19 @@ function f6(shape: DeepReadonly) { let name = shape.name; // string >name : Symbol(name, Decl(mappedTypes2.ts, 89, 7)) ->shape.name : Symbol(name) +>shape.name : Symbol(name, Decl(mappedTypes2.ts, 35, 17)) >shape : Symbol(shape, Decl(mappedTypes2.ts, 88, 12)) ->name : Symbol(name) +>name : Symbol(name, Decl(mappedTypes2.ts, 35, 17)) let location = shape.location; // DeepReadonly >location : Symbol(location, Decl(mappedTypes2.ts, 90, 7)) ->shape.location : Symbol(location) +>shape.location : Symbol(location, Decl(mappedTypes2.ts, 38, 19)) >shape : Symbol(shape, Decl(mappedTypes2.ts, 88, 12)) ->location : Symbol(location) +>location : Symbol(location, Decl(mappedTypes2.ts, 38, 19)) let x = location.x; // number >x : Symbol(x, Decl(mappedTypes2.ts, 91, 7)) ->location.x : Symbol(x) +>location.x : Symbol(x, Decl(mappedTypes2.ts, 30, 17)) >location : Symbol(location, Decl(mappedTypes2.ts, 90, 7)) ->x : Symbol(x) +>x : Symbol(x, Decl(mappedTypes2.ts, 30, 17)) } diff --git a/tests/baselines/reference/mappedTypes3.symbols b/tests/baselines/reference/mappedTypes3.symbols index 683c764f0f4..74b3f3d783a 100644 --- a/tests/baselines/reference/mappedTypes3.symbols +++ b/tests/baselines/reference/mappedTypes3.symbols @@ -71,17 +71,17 @@ function f1(b: Bacon) { let isPerfect = bb.isPerfect.value; >isPerfect : Symbol(isPerfect, Decl(mappedTypes3.ts, 23, 7)) >bb.isPerfect.value : Symbol(Box.value, Decl(mappedTypes3.ts, 0, 14)) ->bb.isPerfect : Symbol(isPerfect) +>bb.isPerfect : Symbol(isPerfect, Decl(mappedTypes3.ts, 11, 17)) >bb : Symbol(bb, Decl(mappedTypes3.ts, 22, 7)) ->isPerfect : Symbol(isPerfect) +>isPerfect : Symbol(isPerfect, Decl(mappedTypes3.ts, 11, 17)) >value : Symbol(Box.value, Decl(mappedTypes3.ts, 0, 14)) let weight = bb.weight.value; >weight : Symbol(weight, Decl(mappedTypes3.ts, 24, 7)) >bb.weight.value : Symbol(Box.value, Decl(mappedTypes3.ts, 0, 14)) ->bb.weight : Symbol(weight) +>bb.weight : Symbol(weight, Decl(mappedTypes3.ts, 12, 23)) >bb : Symbol(bb, Decl(mappedTypes3.ts, 22, 7)) ->weight : Symbol(weight) +>weight : Symbol(weight, Decl(mappedTypes3.ts, 12, 23)) >value : Symbol(Box.value, Decl(mappedTypes3.ts, 0, 14)) } diff --git a/tests/baselines/reference/typeVariableTypeGuards.symbols b/tests/baselines/reference/typeVariableTypeGuards.symbols index fa94cfd9462..d201d0538a1 100644 --- a/tests/baselines/reference/typeVariableTypeGuards.symbols +++ b/tests/baselines/reference/typeVariableTypeGuards.symbols @@ -23,16 +23,16 @@ class A

> { >doSomething : Symbol(A.doSomething, Decl(typeVariableTypeGuards.ts, 7, 22)) this.props.foo && this.props.foo() ->this.props.foo : Symbol(foo) +>this.props.foo : Symbol(foo, Decl(typeVariableTypeGuards.ts, 2, 15)) >this.props : Symbol(A.props, Decl(typeVariableTypeGuards.ts, 6, 33)) >this : Symbol(A, Decl(typeVariableTypeGuards.ts, 4, 1)) >props : Symbol(A.props, Decl(typeVariableTypeGuards.ts, 6, 33)) ->foo : Symbol(foo) ->this.props.foo : Symbol(foo) +>foo : Symbol(foo, Decl(typeVariableTypeGuards.ts, 2, 15)) +>this.props.foo : Symbol(foo, Decl(typeVariableTypeGuards.ts, 2, 15)) >this.props : Symbol(A.props, Decl(typeVariableTypeGuards.ts, 6, 33)) >this : Symbol(A, Decl(typeVariableTypeGuards.ts, 4, 1)) >props : Symbol(A.props, Decl(typeVariableTypeGuards.ts, 6, 33)) ->foo : Symbol(foo) +>foo : Symbol(foo, Decl(typeVariableTypeGuards.ts, 2, 15)) } } From 98893efa118f89009bed5afdc77f67849a8b517e Mon Sep 17 00:00:00 2001 From: Andy Hanson Date: Thu, 25 May 2017 09:00:52 -0700 Subject: [PATCH 15/56] findAllRefs: Replace 'interface State' and 'createState' with just 'class State' --- src/services/findAllReferences.ts | 108 +++++++++++++++--------------- 1 file changed, 54 insertions(+), 54 deletions(-) diff --git a/src/services/findAllReferences.ts b/src/services/findAllReferences.ts index efc6a6f6ed1..833d9ec95f2 100644 --- a/src/services/findAllReferences.ts +++ b/src/services/findAllReferences.ts @@ -386,7 +386,7 @@ namespace ts.FindAllReferences.Core { const searchMeaning = getIntersectingMeaningFromDeclarations(getMeaningFromLocation(node), symbol.declarations); const result: SymbolAndEntries[] = []; - const state = createState(sourceFiles, node, checker, cancellationToken, searchMeaning, options, result); + const state = new State(sourceFiles, node, checker, cancellationToken, searchMeaning, options, result); const search = state.createSearch(node, symbol, /*comingFrom*/ undefined, { allSearchSymbols: populateSearchSymbolSet(symbol, node, checker, options.implementations) }); // Try to get the smallest valid scope that we can limit our search to; @@ -446,35 +446,18 @@ namespace ts.FindAllReferences.Core { * Holds all state needed for the finding references. * Unlike `Search`, there is only one `State`. */ - interface State extends Options { + class State { /** True if we're searching for constructor references. */ readonly isForConstructor: boolean; - readonly sourceFiles: SourceFile[]; - readonly checker: TypeChecker; - readonly cancellationToken: CancellationToken; - readonly searchMeaning: SemanticMeaning; - /** Cache for `explicitlyinheritsFrom`. */ - readonly inheritsFromCache: Map; + readonly inheritsFromCache = createMap(); - /** Gets every place to look for references of an exported symbols. See `ImportsResult` in `importTracker.ts` for more documentation. */ - getImportSearches(exportSymbol: Symbol, exportInfo: ExportInfo): ImportsResult; + private readonly symbolIdToReferences: Entry[][] = []; + // Source file ID → symbol ID → Whether the symbol has been searched for in the source file. + private readonly sourceFileToSeenSymbols: Array> = []; - /** @param allSearchSymbols set of additinal symbols for use by `includes`. */ - createSearch(location: Node, symbol: Symbol, comingFrom: ImportExport | undefined, searchOptions?: { text?: string, allSearchSymbols?: Symbol[] }): Search; - - /** - * Callback to add references for a particular searched symbol. - * This initializes a reference group, so only call this if you will add at least one reference. - */ - referenceAdder(searchSymbol: Symbol, searchLocation: Node): (node: Node) => void; - - /** Add a reference with no associated definition. */ - addStringOrCommentReference(fileName: string, textSpan: TextSpan): void; - - /** Returns `true` the first time we search for a symbol in a file and `false` afterwards. */ - markSearchedSymbol(sourceFile: SourceFile, symbol: Symbol): boolean; + private importTracker: ImportTracker | undefined; /** * Type nodes can contain multiple references to the same type. For example: @@ -483,7 +466,7 @@ namespace ts.FindAllReferences.Core { * duplicate entries would be returned here as each of the type references is part of * the same implementation. For that reason, check before we add a new entry. */ - markSeenContainingTypeReference(containingTypeReference: Node): boolean; + readonly markSeenContainingTypeReference: (containingTypeReference: Node) => boolean; /** * It's possible that we will encounter the right side of `export { foo as bar } from "x";` more than once. @@ -496,33 +479,44 @@ namespace ts.FindAllReferences.Core { * But another reference to it may appear in the same source file. * See `tests/cases/fourslash/transitiveExportImports3.ts`. */ - markSeenReExportRHS(rhs: Identifier): boolean; - } + readonly markSeenReExportRHS: (rhs: Identifier) => boolean; - function createState(sourceFiles: SourceFile[], originalLocation: Node, checker: TypeChecker, cancellationToken: CancellationToken, searchMeaning: SemanticMeaning, options: Options, result: Push): State { - const symbolIdToReferences: Entry[][] = []; - const inheritsFromCache = createMap(); - // Source file ID → symbol ID → Whether the symbol has been searched for in the source file. - const sourceFileToSeenSymbols: Array> = []; - const isForConstructor = originalLocation.kind === SyntaxKind.ConstructorKeyword; - let importTracker: ImportTracker | undefined; + readonly findInStrings?: boolean; + readonly findInComments?: boolean; + readonly isForRename?: boolean; + readonly implementations?: boolean; - return { - ...options, - sourceFiles, isForConstructor, checker, cancellationToken, searchMeaning, inheritsFromCache, getImportSearches, createSearch, referenceAdder, addStringOrCommentReference, - markSearchedSymbol, markSeenContainingTypeReference: nodeSeenTracker(), markSeenReExportRHS: nodeSeenTracker(), - }; + constructor( + readonly sourceFiles: SourceFile[], + originalLocation: Node, + readonly checker: TypeChecker, + readonly cancellationToken: CancellationToken, + readonly searchMeaning: SemanticMeaning, + options: Options, + private readonly result: Push) { - function getImportSearches(exportSymbol: Symbol, exportInfo: ExportInfo): ImportsResult { - if (!importTracker) importTracker = createImportTracker(sourceFiles, checker, cancellationToken); - return importTracker(exportSymbol, exportInfo, options.isForRename); + this.findInStrings = options.findInStrings; + this.findInComments = options.findInComments; + this.isForRename = options.isForRename; + this.implementations = options.implementations; + + this.isForConstructor = originalLocation.kind === SyntaxKind.ConstructorKeyword; + this.markSeenContainingTypeReference = nodeSeenTracker(); + this.markSeenReExportRHS = nodeSeenTracker(); } - function createSearch(location: Node, symbol: Symbol, comingFrom: ImportExport, searchOptions: { text?: string, allSearchSymbols?: Symbol[] } = {}): Search { + /** Gets every place to look for references of an exported symbols. See `ImportsResult` in `importTracker.ts` for more documentation. */ + getImportSearches(exportSymbol: Symbol, exportInfo: ExportInfo): ImportsResult { + if (!this.importTracker) this.importTracker = createImportTracker(this.sourceFiles, this.checker, this.cancellationToken); + return this.importTracker(exportSymbol, exportInfo, this.isForRename); + } + + /** @param allSearchSymbols set of additinal symbols for use by `includes`. */ + createSearch(location: Node, symbol: Symbol, comingFrom: ImportExport | undefined, searchOptions: { text?: string, allSearchSymbols?: Symbol[] } = {}): Search { // Note: if this is an external module symbol, the name doesn't include quotes. - const { text = stripQuotes(getDeclaredName(checker, symbol, location)), allSearchSymbols = undefined } = searchOptions; + const { text = stripQuotes(getDeclaredName(this.checker, symbol, location)), allSearchSymbols = undefined } = searchOptions; const escapedText = escapeIdentifier(text); - const parents = options.implementations && getParentSymbolsOfPropertyAccess(location, symbol, checker); + const parents = this.implementations && getParentSymbolsOfPropertyAccess(location, symbol, this.checker); return { location, symbol, comingFrom, text, escapedText, parents, includes }; function includes(referenceSymbol: Symbol): boolean { @@ -530,27 +524,33 @@ namespace ts.FindAllReferences.Core { } } - function referenceAdder(referenceSymbol: Symbol, searchLocation: Node): (node: Node) => void { - const symbolId = getSymbolId(referenceSymbol); - let references = symbolIdToReferences[symbolId]; + /** + * Callback to add references for a particular searched symbol. + * This initializes a reference group, so only call this if you will add at least one reference. + */ + referenceAdder(searchSymbol: Symbol, searchLocation: Node): (node: Node) => void { + const symbolId = getSymbolId(searchSymbol); + let references = this.symbolIdToReferences[symbolId]; if (!references) { - references = symbolIdToReferences[symbolId] = []; - result.push({ definition: { type: "symbol", symbol: referenceSymbol, node: searchLocation }, references }); + references = this.symbolIdToReferences[symbolId] = []; + this.result.push({ definition: { type: "symbol", symbol: searchSymbol, node: searchLocation }, references }); } return node => references.push(nodeEntry(node)); } - function addStringOrCommentReference(fileName: string, textSpan: TextSpan): void { - result.push({ + /** Add a reference with no associated definition. */ + addStringOrCommentReference(fileName: string, textSpan: TextSpan): void { + this.result.push({ definition: undefined, references: [{ type: "span", fileName, textSpan }] }); } - function markSearchedSymbol(sourceFile: SourceFile, symbol: Symbol): boolean { + /** Returns `true` the first time we search for a symbol in a file and `false` afterwards. */ + markSearchedSymbol(sourceFile: SourceFile, symbol: Symbol): boolean { const sourceId = getNodeId(sourceFile); const symbolId = getSymbolId(symbol); - const seenSymbols = sourceFileToSeenSymbols[sourceId] || (sourceFileToSeenSymbols[sourceId] = []); + const seenSymbols = this.sourceFileToSeenSymbols[sourceId] || (this.sourceFileToSeenSymbols[sourceId] = []); return !seenSymbols[symbolId] && (seenSymbols[symbolId] = true); } } From 528a59fdde73c3d435dbb9bdce1163fe1303b8ad Mon Sep 17 00:00:00 2001 From: Andy Hanson Date: Thu, 25 May 2017 10:23:04 -0700 Subject: [PATCH 16/56] Clean up instance variables --- src/services/findAllReferences.ts | 59 +++++++++++-------------------- 1 file changed, 20 insertions(+), 39 deletions(-) diff --git a/src/services/findAllReferences.ts b/src/services/findAllReferences.ts index 833d9ec95f2..f3b20637acd 100644 --- a/src/services/findAllReferences.ts +++ b/src/services/findAllReferences.ts @@ -386,7 +386,7 @@ namespace ts.FindAllReferences.Core { const searchMeaning = getIntersectingMeaningFromDeclarations(getMeaningFromLocation(node), symbol.declarations); const result: SymbolAndEntries[] = []; - const state = new State(sourceFiles, node, checker, cancellationToken, searchMeaning, options, result); + const state = new State(sourceFiles, /*isForConstructor*/ node.kind === SyntaxKind.ConstructorKeyword, checker, cancellationToken, searchMeaning, options, result); const search = state.createSearch(node, symbol, /*comingFrom*/ undefined, { allSearchSymbols: populateSearchSymbolSet(symbol, node, checker, options.implementations) }); // Try to get the smallest valid scope that we can limit our search to; @@ -447,18 +447,9 @@ namespace ts.FindAllReferences.Core { * Unlike `Search`, there is only one `State`. */ class State { - /** True if we're searching for constructor references. */ - readonly isForConstructor: boolean; - /** Cache for `explicitlyinheritsFrom`. */ readonly inheritsFromCache = createMap(); - private readonly symbolIdToReferences: Entry[][] = []; - // Source file ID → symbol ID → Whether the symbol has been searched for in the source file. - private readonly sourceFileToSeenSymbols: Array> = []; - - private importTracker: ImportTracker | undefined; - /** * Type nodes can contain multiple references to the same type. For example: * let x: Foo & (Foo & Bar) = ... @@ -466,7 +457,7 @@ namespace ts.FindAllReferences.Core { * duplicate entries would be returned here as each of the type references is part of * the same implementation. For that reason, check before we add a new entry. */ - readonly markSeenContainingTypeReference: (containingTypeReference: Node) => boolean; + readonly markSeenContainingTypeReference = nodeSeenTracker(); /** * It's possible that we will encounter the right side of `export { foo as bar } from "x";` more than once. @@ -479,36 +470,23 @@ namespace ts.FindAllReferences.Core { * But another reference to it may appear in the same source file. * See `tests/cases/fourslash/transitiveExportImports3.ts`. */ - readonly markSeenReExportRHS: (rhs: Identifier) => boolean; - - readonly findInStrings?: boolean; - readonly findInComments?: boolean; - readonly isForRename?: boolean; - readonly implementations?: boolean; + readonly markSeenReExportRHS = nodeSeenTracker(); constructor( readonly sourceFiles: SourceFile[], - originalLocation: Node, + /** True if we're searching for constructor references. */ + readonly isForConstructor: boolean, readonly checker: TypeChecker, readonly cancellationToken: CancellationToken, readonly searchMeaning: SemanticMeaning, - options: Options, - private readonly result: Push) { - - this.findInStrings = options.findInStrings; - this.findInComments = options.findInComments; - this.isForRename = options.isForRename; - this.implementations = options.implementations; - - this.isForConstructor = originalLocation.kind === SyntaxKind.ConstructorKeyword; - this.markSeenContainingTypeReference = nodeSeenTracker(); - this.markSeenReExportRHS = nodeSeenTracker(); - } + readonly options: Options, + private readonly result: Push) {} + private importTracker: ImportTracker | undefined; /** Gets every place to look for references of an exported symbols. See `ImportsResult` in `importTracker.ts` for more documentation. */ getImportSearches(exportSymbol: Symbol, exportInfo: ExportInfo): ImportsResult { if (!this.importTracker) this.importTracker = createImportTracker(this.sourceFiles, this.checker, this.cancellationToken); - return this.importTracker(exportSymbol, exportInfo, this.isForRename); + return this.importTracker(exportSymbol, exportInfo, this.options.isForRename); } /** @param allSearchSymbols set of additinal symbols for use by `includes`. */ @@ -516,7 +494,7 @@ namespace ts.FindAllReferences.Core { // Note: if this is an external module symbol, the name doesn't include quotes. const { text = stripQuotes(getDeclaredName(this.checker, symbol, location)), allSearchSymbols = undefined } = searchOptions; const escapedText = escapeIdentifier(text); - const parents = this.implementations && getParentSymbolsOfPropertyAccess(location, symbol, this.checker); + const parents = this.options.implementations && getParentSymbolsOfPropertyAccess(location, symbol, this.checker); return { location, symbol, comingFrom, text, escapedText, parents, includes }; function includes(referenceSymbol: Symbol): boolean { @@ -524,6 +502,7 @@ namespace ts.FindAllReferences.Core { } } + private readonly symbolIdToReferences: Entry[][] = []; /** * Callback to add references for a particular searched symbol. * This initializes a reference group, so only call this if you will add at least one reference. @@ -546,6 +525,8 @@ namespace ts.FindAllReferences.Core { }); } + // Source file ID → symbol ID → Whether the symbol has been searched for in the source file. + private readonly sourceFileToSeenSymbols: Array> = []; /** Returns `true` the first time we search for a symbol in a file and `false` afterwards. */ markSearchedSymbol(sourceFile: SourceFile, symbol: Symbol): boolean { const sourceId = getNodeId(sourceFile); @@ -580,7 +561,7 @@ namespace ts.FindAllReferences.Core { break; case ExportKind.Default: // Search for a property access to '.default'. This can't be renamed. - indirectSearch = state.isForRename ? undefined : state.createSearch(exportLocation, exportSymbol, ImportExport.Export, { text: "default" }); + indirectSearch = state.options.isForRename ? undefined : state.createSearch(exportLocation, exportSymbol, ImportExport.Export, { text: "default" }); break; case ExportKind.ExportEquals: break; @@ -806,7 +787,7 @@ namespace ts.FindAllReferences.Core { return; } - for (const position of getPossibleSymbolReferencePositions(sourceFile, search.text, container, /*fullStart*/ state.findInComments || container.jsDoc !== undefined)) { + for (const position of getPossibleSymbolReferencePositions(sourceFile, search.text, container, /*fullStart*/ state.options.findInComments || container.jsDoc !== undefined)) { getReferencesAtLocation(sourceFile, position, search, state); } } @@ -818,7 +799,7 @@ namespace ts.FindAllReferences.Core { // This wasn't the start of a token. Check to see if it might be a // match in a comment or string if that's what the caller is asking // for. - if (!state.implementations && (state.findInStrings && isInString(sourceFile, position) || state.findInComments && isInNonReferenceComment(sourceFile, position))) { + if (!state.options.implementations && (state.options.findInStrings && isInString(sourceFile, position) || state.options.findInComments && isInNonReferenceComment(sourceFile, position))) { // In the case where we're looking inside comments/strings, we don't have // an actual definition. So just use 'undefined' here. Features like // 'Rename' won't care (as they ignore the definitions), and features like @@ -884,7 +865,7 @@ namespace ts.FindAllReferences.Core { addRef(); } - if (!state.isForRename && state.markSeenReExportRHS(name)) { + if (!state.options.isForRename && state.markSeenReExportRHS(name)) { addReference(name, referenceSymbol, name, state); } } @@ -895,7 +876,7 @@ namespace ts.FindAllReferences.Core { } // For `export { foo as bar }`, rename `foo`, but not `bar`. - if (!(referenceLocation === propertyName && state.isForRename)) { + if (!(referenceLocation === propertyName && state.options.isForRename)) { const exportKind = (referenceLocation as Identifier).originalKeywordKind === ts.SyntaxKind.DefaultKeyword ? ExportKind.Default : ExportKind.Named; const exportInfo = getExportInfo(referenceSymbol, exportKind, state.checker); Debug.assert(!!exportInfo); @@ -937,7 +918,7 @@ namespace ts.FindAllReferences.Core { const { symbol } = importOrExport; if (importOrExport.kind === ImportExport.Import) { - if (!state.isForRename || importOrExport.isNamedImport) { + if (!state.options.isForRename || importOrExport.isNamedImport) { searchForImportedSymbol(symbol, state); } } @@ -963,7 +944,7 @@ namespace ts.FindAllReferences.Core { function addReference(referenceLocation: Node, relatedSymbol: Symbol, searchLocation: Node, state: State): void { const addRef = state.referenceAdder(relatedSymbol, searchLocation); - if (state.implementations) { + if (state.options.implementations) { addImplementationReferences(referenceLocation, addRef, state); } else { From 2e6f31f8e0fca508772d804417bf23677b17953e Mon Sep 17 00:00:00 2001 From: Mohamed Hegazy Date: Thu, 25 May 2017 12:23:15 -0700 Subject: [PATCH 17/56] Use tslint@latest (#16049) * Use tslint@latest * use latest gulp-typescript --- package.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index ea3262902b1..c62fa46853b 100644 --- a/package.json +++ b/package.json @@ -59,7 +59,7 @@ "gulp-insert": "latest", "gulp-newer": "latest", "gulp-sourcemaps": "latest", - "gulp-typescript": "3.1.5", + "gulp-typescript": "latest", "into-stream": "latest", "istanbul": "latest", "jake": "latest", @@ -74,7 +74,7 @@ "through2": "latest", "travis-fold": "latest", "ts-node": "latest", - "tslint": "next", + "tslint": "latest", "typescript": "next" }, "scripts": { From d052bb83caaee1f4024ecf8dfa12fa720544db3e Mon Sep 17 00:00:00 2001 From: Andy Date: Thu, 25 May 2017 13:30:27 -0700 Subject: [PATCH 18/56] Add project telemetry (#16050) * Add project telemetry * Respond to some PR comments * Wrap event in a TelemetryEvent payload * Replace paths with empty string instead of removing them entirely * Add "version" property to payload * Add telemetry for typeAcquisition settings * Add "files", "include", "exclude", and "compileOnSave" * Convert typingsOptions include and exclude to booleanss * Add "extends", "configFileName", and "projectType" * configFileName: Use "other" instead of undefined * Add "languageServiceEnabled" telemetry --- Jakefile.js | 1 + src/compiler/commandLineParser.ts | 67 +++- src/compiler/core.ts | 12 + src/harness/tsconfig.json | 3 +- src/harness/unittests/telemetry.ts | 291 ++++++++++++++++++ .../unittests/tsserverProjectSystem.ts | 4 +- src/harness/unittests/typingsInstaller.ts | 28 +- src/server/editorServices.ts | 103 ++++++- src/server/project.ts | 16 +- src/server/session.ts | 11 +- src/server/utilities.ts | 5 +- 11 files changed, 505 insertions(+), 36 deletions(-) create mode 100644 src/harness/unittests/telemetry.ts diff --git a/Jakefile.js b/Jakefile.js index 577ade2ef69..8ba4bd2f4e1 100644 --- a/Jakefile.js +++ b/Jakefile.js @@ -129,6 +129,7 @@ var harnessSources = harnessCoreSources.concat([ "initializeTSConfig.ts", "printer.ts", "textChanges.ts", + "telemetry.ts", "transform.ts", "customTransforms.ts", ].map(function (f) { diff --git a/src/compiler/commandLineParser.ts b/src/compiler/commandLineParser.ts index 88687357115..e612378671d 100644 --- a/src/compiler/commandLineParser.ts +++ b/src/compiler/commandLineParser.ts @@ -692,8 +692,7 @@ namespace ts { return typeAcquisition; } - /* @internal */ - export function getOptionNameMap(): OptionNameMap { + function getOptionNameMap(): OptionNameMap { if (optionNameMapCache) { return optionNameMapCache; } @@ -746,7 +745,6 @@ namespace ts { const options: CompilerOptions = {}; const fileNames: string[] = []; const errors: Diagnostic[] = []; - const { optionNameMap, shortOptionNames } = getOptionNameMap(); parseStrings(commandLine); return { @@ -758,21 +756,13 @@ namespace ts { function parseStrings(args: string[]) { let i = 0; while (i < args.length) { - let s = args[i]; + const s = args[i]; i++; if (s.charCodeAt(0) === CharacterCodes.at) { parseResponseFile(s.slice(1)); } else if (s.charCodeAt(0) === CharacterCodes.minus) { - s = s.slice(s.charCodeAt(1) === CharacterCodes.minus ? 2 : 1).toLowerCase(); - - // Try to translate short option names to their full equivalents. - const short = shortOptionNames.get(s); - if (short !== undefined) { - s = short; - } - - const opt = optionNameMap.get(s); + const opt = getOptionFromName(s.slice(s.charCodeAt(1) === CharacterCodes.minus ? 2 : 1), /*allowShort*/ true); if (opt) { if (opt.isTSConfigOnly) { errors.push(createCompilerDiagnostic(Diagnostics.Option_0_can_only_be_specified_in_tsconfig_json_file, opt.name)); @@ -860,6 +850,19 @@ namespace ts { } } + function getOptionFromName(optionName: string, allowShort = false): CommandLineOption | undefined { + optionName = optionName.toLowerCase(); + const { optionNameMap, shortOptionNames } = getOptionNameMap(); + // Try to translate short option names to their full equivalents. + if (allowShort) { + const short = shortOptionNames.get(optionName); + if (short !== undefined) { + optionName = short; + } + } + return optionNameMap.get(optionName); + } + /** * Read tsconfig.json file * @param fileName The path to the config file @@ -1705,4 +1708,42 @@ namespace ts { function caseInsensitiveKeyMapper(key: string) { return key.toLowerCase(); } + + /** + * Produces a cleaned version of compiler options with personally identifiying info (aka, paths) removed. + * Also converts enum values back to strings. + */ + /* @internal */ + export function convertCompilerOptionsForTelemetry(opts: ts.CompilerOptions): ts.CompilerOptions { + const out: ts.CompilerOptions = {}; + for (const key in opts) if (opts.hasOwnProperty(key)) { + const type = getOptionFromName(key); + if (type !== undefined) { // Ignore unknown options + out[key] = getOptionValueWithEmptyStrings(opts[key], type); + } + } + return out; + } + + function getOptionValueWithEmptyStrings(value: any, option: CommandLineOption): {} { + switch (option.type) { + case "object": // "paths". Can't get any useful information from the value since we blank out strings, so just return "". + return ""; + case "string": // Could be any arbitrary string -- use empty string instead. + return ""; + case "number": // Allow numbers, but be sure to check it's actually a number. + return typeof value === "number" ? value : ""; + case "boolean": + return typeof value === "boolean" ? value : ""; + case "list": + const elementType = (option as CommandLineOptionOfListType).element; + return ts.isArray(value) ? value.map(v => getOptionValueWithEmptyStrings(v, elementType)) : ""; + default: + return ts.forEachEntry(option.type, (optionEnumValue, optionStringValue) => { + if (optionEnumValue === value) { + return optionStringValue; + } + }); + } + } } diff --git a/src/compiler/core.ts b/src/compiler/core.ts index 52a7b5f5a7a..d1d21e94694 100644 --- a/src/compiler/core.ts +++ b/src/compiler/core.ts @@ -521,6 +521,18 @@ namespace ts { return result || array; } + export function mapDefined(array: ReadonlyArray, mapFn: (x: T, i: number) => T | undefined): ReadonlyArray { + const result: T[] = []; + for (let i = 0; i < array.length; i++) { + const item = array[i]; + const mapped = mapFn(item, i); + if (mapped !== undefined) { + result.push(mapped); + } + } + return result; + } + /** * Computes the first matching span of elements and returns a tuple of the first span * and the remaining elements. diff --git a/src/harness/tsconfig.json b/src/harness/tsconfig.json index d752c0f235b..6553f3667a7 100644 --- a/src/harness/tsconfig.json +++ b/src/harness/tsconfig.json @@ -127,6 +127,7 @@ "./unittests/printer.ts", "./unittests/transform.ts", "./unittests/customTransforms.ts", - "./unittests/textChanges.ts" + "./unittests/textChanges.ts", + "./unittests/telemetry.ts" ] } diff --git a/src/harness/unittests/telemetry.ts b/src/harness/unittests/telemetry.ts new file mode 100644 index 00000000000..d3811edf251 --- /dev/null +++ b/src/harness/unittests/telemetry.ts @@ -0,0 +1,291 @@ +/// +/// + +namespace ts.projectSystem { + describe("project telemetry", () => { + it("does nothing for inferred project", () => { + const file = makeFile("/a.js"); + const et = new EventTracker([file]); + et.service.openClientFile(file.path); + assert.equal(et.getEvents().length, 0); + }); + it("only sends an event once", () => { + const file = makeFile("/a.ts"); + const tsconfig = makeFile("/tsconfig.json", {}); + + const et = new EventTracker([file, tsconfig]); + et.service.openClientFile(file.path); + et.assertProjectInfoTelemetryEvent({}); + + et.service.closeClientFile(file.path); + checkNumberOfProjects(et.service, { configuredProjects: 0 }); + + et.service.openClientFile(file.path); + checkNumberOfProjects(et.service, { configuredProjects: 1 }); + + assert.equal(et.getEvents().length, 0); + }); + + it("counts files by extension", () => { + const files = ["ts.ts", "tsx.tsx", "moo.ts", "dts.d.ts", "jsx.jsx", "js.js", "badExtension.badExtension"].map(f => makeFile(`/src/${f}`)); + const notIncludedFile = makeFile("/bin/ts.js"); + const compilerOptions: ts.CompilerOptions = { allowJs: true }; + const tsconfig = makeFile("/tsconfig.json", { compilerOptions, include: ["src"] }); + + const et = new EventTracker([...files, notIncludedFile, tsconfig]); + et.service.openClientFile(files[0].path); + et.assertProjectInfoTelemetryEvent({ + fileStats: { ts: 2, tsx: 1, js: 1, jsx: 1, dts: 1 }, + compilerOptions, + include: true, + }); + }); + + it("works with external project", () => { + const file1 = makeFile("/a.ts"); + const et = new EventTracker([file1]); + const compilerOptions: ts.CompilerOptions = { strict: true }; + + const projectFileName = "foo.csproj"; + + open(); + + // TODO: Apparently compilerOptions is mutated, so have to repeat it here! + et.assertProjectInfoTelemetryEvent({ + compilerOptions: { strict: true }, + compileOnSave: true, + // These properties can't be present for an external project, so they are undefined instead of false. + extends: undefined, + files: undefined, + include: undefined, + exclude: undefined, + configFileName: "other", + projectType: "external", + }); + + // Also test that opening an external project only sends an event once. + + et.service.closeExternalProject(projectFileName); + checkNumberOfProjects(et.service, { externalProjects: 0 }); + + open(); + assert.equal(et.getEvents().length, 0); + + function open(): void { + et.service.openExternalProject({ + rootFiles: toExternalFiles([file1.path]), + options: compilerOptions, + projectFileName: projectFileName, + }); + checkNumberOfProjects(et.service, { externalProjects: 1 }); + } + }); + + it("does not expose paths", () => { + const file = makeFile("/a.ts"); + + const compilerOptions: ts.CompilerOptions = { + project: "", + outFile: "hunter2.js", + outDir: "hunter2", + rootDir: "hunter2", + baseUrl: "hunter2", + rootDirs: ["hunter2"], + typeRoots: ["hunter2"], + types: ["hunter2"], + sourceRoot: "hunter2", + mapRoot: "hunter2", + jsxFactory: "hunter2", + out: "hunter2", + reactNamespace: "hunter2", + charset: "hunter2", + locale: "hunter2", + declarationDir: "hunter2", + paths: { + "*": ["hunter2"], + }, + + // Boolean / number options get through + declaration: true, + + // List of string enum gets through -- but only if legitimately a member of the enum + lib: ["es6", "dom", "hunter2"], + + // Sensitive data doesn't get through even if sent to an option of safe type + checkJs: "hunter2" as any as boolean, + }; + const safeCompilerOptions: ts.CompilerOptions = { + project: "", + outFile: "", + outDir: "", + rootDir: "", + baseUrl: "", + rootDirs: [""], + typeRoots: [""], + types: [""], + sourceRoot: "", + mapRoot: "", + jsxFactory: "", + out: "", + reactNamespace: "", + charset: "", + locale: "", + declarationDir: "", + paths: "" as any, + + declaration: true, + + lib: ["es6", "dom"], + + checkJs: "" as any as boolean, + }; + (compilerOptions as any).unknownCompilerOption = "hunter2"; // These are always ignored. + const tsconfig = makeFile("/tsconfig.json", { compilerOptions, files: ["/a.ts"] }); + + const et = new EventTracker([file, tsconfig]); + et.service.openClientFile(file.path); + + et.assertProjectInfoTelemetryEvent({ + compilerOptions: safeCompilerOptions, + files: true, + }); + }); + + it("sends telemetry for extends, files, include, exclude, and compileOnSave", () => { + const file = makeFile("/hunter2/a.ts"); + const tsconfig = makeFile("/tsconfig.json", { + compilerOptions: {}, + extends: "hunter2.json", + files: ["hunter2/a.ts"], + include: ["hunter2"], + exclude: ["hunter2"], + compileOnSave: true, + }); + + const et = new EventTracker([tsconfig, file]); + et.service.openClientFile(file.path); + et.assertProjectInfoTelemetryEvent({ + extends: true, + files: true, + include: true, + exclude: true, + compileOnSave: true, + }); + }); + + const autoJsCompilerOptions = { + // Apparently some options are added by default. + allowJs: true, + allowSyntheticDefaultImports: true, + maxNodeModuleJsDepth: 2, + skipLibCheck: true, + }; + + it("sends telemetry for typeAcquisition settings", () => { + const file = makeFile("/a.js"); + const jsconfig = makeFile("/jsconfig.json", { + compilerOptions: {}, + typeAcquisition: { + enable: true, + enableAutoDiscovery: false, + include: ["hunter2", "hunter3"], + exclude: [], + }, + }); + const et = new EventTracker([jsconfig, file]); + et.service.openClientFile(file.path); + et.assertProjectInfoTelemetryEvent({ + fileStats: fileStats({ js: 1 }), + compilerOptions: autoJsCompilerOptions, + typeAcquisition: { + enable: true, + include: true, + exclude: false, + }, + configFileName: "jsconfig.json", + }); + }); + + it("detects whether language service was disabled", () => { + const file = makeFile("/a.js"); + const tsconfig = makeFile("/jsconfig.json", {}); + const et = new EventTracker([tsconfig, file]); + et.host.getFileSize = () => server.maxProgramSizeForNonTsFiles + 1; + et.service.openClientFile(file.path); + et.getEvent(server.ProjectLanguageServiceStateEvent, /*mayBeMore*/ true); + et.assertProjectInfoTelemetryEvent({ + fileStats: fileStats({ js: 1 }), + compilerOptions: autoJsCompilerOptions, + configFileName: "jsconfig.json", + typeAcquisition: { + enable: true, + include: false, + exclude: false, + }, + languageServiceEnabled: false, + }); + }); + }); + + class EventTracker { + private events: server.ProjectServiceEvent[] = []; + readonly service: TestProjectService; + readonly host: projectSystem.TestServerHost; + + constructor(files: projectSystem.FileOrFolder[]) { + this.host = createServerHost(files); + this.service = createProjectService(this.host, { + eventHandler: event => { + this.events.push(event); + }, + }); + } + + getEvents(): ReadonlyArray { + const events = this.events; + this.events = []; + return events; + } + + assertProjectInfoTelemetryEvent(partial: Partial): void { + assert.deepEqual(this.getEvent(ts.server.ProjectInfoTelemetryEvent), makePayload(partial)); + } + + getEvent(eventName: T["eventName"], mayBeMore = false): T["data"] { + if (mayBeMore) assert(this.events.length !== 0); else assert.equal(this.events.length, 1); + const event = this.events.shift(); + assert.equal(event.eventName, eventName); + return event.data; + } + } + + function makePayload(partial: Partial): server.ProjectInfoTelemetryEventData { + return { + fileStats: fileStats({ ts: 1 }), + compilerOptions: {}, + extends: false, + files: false, + include: false, + exclude: false, + compileOnSave: false, + typeAcquisition: { + enable: false, + exclude: false, + include: false, + }, + configFileName: "tsconfig.json", + projectType: "configured", + languageServiceEnabled: true, + version: ts.version, + ...partial + }; + } + + function makeFile(path: string, content: {} = ""): projectSystem.FileOrFolder { + return { path, content: typeof content === "string" ? "" : JSON.stringify(content) }; + } + + function fileStats(nonZeroStats: Partial): server.FileStats { + return { ts: 0, tsx: 0, dts: 0, js: 0, jsx: 0, ...nonZeroStats }; + } +} diff --git a/src/harness/unittests/tsserverProjectSystem.ts b/src/harness/unittests/tsserverProjectSystem.ts index efa92490300..6f898e7f4a6 100644 --- a/src/harness/unittests/tsserverProjectSystem.ts +++ b/src/harness/unittests/tsserverProjectSystem.ts @@ -2234,7 +2234,7 @@ namespace ts.projectSystem { let lastEvent: server.ProjectLanguageServiceStateEvent; const session = createSession(host, /*typingsInstaller*/ undefined, e => { - if (e.eventName === server.ConfigFileDiagEvent || e.eventName === server.ContextEvent) { + if (e.eventName === server.ConfigFileDiagEvent || e.eventName === server.ContextEvent || e.eventName === server.ProjectInfoTelemetryEvent) { return; } assert.equal(e.eventName, server.ProjectLanguageServiceStateEvent); @@ -2284,7 +2284,7 @@ namespace ts.projectSystem { filePath === f2.path ? server.maxProgramSizeForNonTsFiles + 1 : originalGetFileSize.call(host, filePath); let lastEvent: server.ProjectLanguageServiceStateEvent; const session = createSession(host, /*typingsInstaller*/ undefined, e => { - if (e.eventName === server.ConfigFileDiagEvent) { + if (e.eventName === server.ConfigFileDiagEvent || e.eventName === server.ProjectInfoTelemetryEvent) { return; } assert.equal(e.eventName, server.ProjectLanguageServiceStateEvent); diff --git a/src/harness/unittests/typingsInstaller.ts b/src/harness/unittests/typingsInstaller.ts index af95874a32c..699b1807428 100644 --- a/src/harness/unittests/typingsInstaller.ts +++ b/src/harness/unittests/typingsInstaller.ts @@ -44,7 +44,7 @@ namespace ts.projectSystem { }); } - import typingsName = server.typingsInstaller.typingsName; + import typingsName = TI.typingsName; describe("local module", () => { it("should not be picked up", () => { @@ -73,7 +73,7 @@ namespace ts.projectSystem { constructor() { super(host, { typesRegistry: createTypesRegistry("config"), globalTypingsCacheLocation: typesCache }); } - installWorker(_requestId: number, _args: string[], _cwd: string, _cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, _cb: TI.RequestCompletedAction) { assert(false, "should not be called"); } })(); @@ -121,7 +121,7 @@ namespace ts.projectSystem { constructor() { super(host, { typesRegistry: createTypesRegistry("jquery") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/jquery"]; const typingFiles = [jquery]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -165,7 +165,7 @@ namespace ts.projectSystem { constructor() { super(host, { typesRegistry: createTypesRegistry("jquery") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/jquery"]; const typingFiles = [jquery]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -672,7 +672,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: "/tmp", typesRegistry: createTypesRegistry("jquery") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/jquery"]; const typingFiles = [jqueryDTS]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -718,7 +718,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: "/tmp", typesRegistry: createTypesRegistry("jquery") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/jquery"]; const typingFiles = [jqueryDTS]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -765,7 +765,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: "/tmp", typesRegistry: createTypesRegistry("jquery") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/jquery"]; const typingFiles = [jqueryDTS]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -808,7 +808,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: cachePath, typesRegistry: createTypesRegistry("commander") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/commander"]; const typingFiles = [commander]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -849,7 +849,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: cachePath, typesRegistry: createTypesRegistry("node", "commander") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/node", "@types/commander"]; const typingFiles = [node, commander]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -888,7 +888,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: "/tmp", typesRegistry: createTypesRegistry("foo") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { executeCommand(this, host, ["foo"], [], cb); } })(); @@ -996,7 +996,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: "/tmp" }, { isEnabled: () => true, writeLine: msg => messages.push(msg) }); } - installWorker(_requestId: number, _args: string[], _cwd: string, _cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, _cb: TI.RequestCompletedAction) { assert(false, "runCommand should not be invoked"); } })(); @@ -1060,7 +1060,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: cachePath, typesRegistry: createTypesRegistry("commander") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/commander"]; const typingFiles = [commander]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -1110,7 +1110,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: cachePath, typesRegistry: createTypesRegistry("commander") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { const installedTypings = ["@types/commander"]; const typingFiles = [commander]; executeCommand(this, host, installedTypings, typingFiles, cb); @@ -1157,7 +1157,7 @@ namespace ts.projectSystem { constructor() { super(host, { globalTypingsCacheLocation: cachePath, typesRegistry: createTypesRegistry("commander") }); } - installWorker(_requestId: number, _args: string[], _cwd: string, cb: server.typingsInstaller.RequestCompletedAction) { + installWorker(_requestId: number, _args: string[], _cwd: string, cb: TI.RequestCompletedAction) { executeCommand(this, host, "", [], cb); } sendResponse(response: server.SetTypings | server.InvalidateCachedTypings | server.BeginInstallTypes | server.EndInstallTypes) { diff --git a/src/server/editorServices.ts b/src/server/editorServices.ts index d8322f5e7c5..7c0e0a0fb92 100644 --- a/src/server/editorServices.ts +++ b/src/server/editorServices.ts @@ -13,6 +13,7 @@ namespace ts.server { export const ContextEvent = "context"; export const ConfigFileDiagEvent = "configFileDiag"; export const ProjectLanguageServiceStateEvent = "projectLanguageServiceState"; + export const ProjectInfoTelemetryEvent = "projectInfo"; export interface ContextEvent { eventName: typeof ContextEvent; @@ -29,7 +30,52 @@ namespace ts.server { data: { project: Project, languageServiceEnabled: boolean }; } - export type ProjectServiceEvent = ContextEvent | ConfigFileDiagEvent | ProjectLanguageServiceStateEvent; + /** This will be converted to the payload of a protocol.TelemetryEvent in session.defaultEventHandler. */ + export interface ProjectInfoTelemetryEvent { + readonly eventName: typeof ProjectInfoTelemetryEvent; + readonly data: ProjectInfoTelemetryEventData; + } + + export interface ProjectInfoTelemetryEventData { + /** Count of file extensions seen in the project. */ + readonly fileStats: FileStats; + /** + * Any compiler options that might contain paths will be taken out. + * Enum compiler options will be converted to strings. + */ + readonly compilerOptions: ts.CompilerOptions; + // "extends", "files", "include", or "exclude" will be undefined if an external config is used. + // Otherwise, we will use "true" if the property is present and "false" if it is missing. + readonly extends: boolean | undefined; + readonly files: boolean | undefined; + readonly include: boolean | undefined; + readonly exclude: boolean | undefined; + readonly compileOnSave: boolean; + readonly typeAcquisition: ProjectInfoTypeAcquisitionData; + + readonly configFileName: "tsconfig.json" | "jsconfig.json" | "other"; + readonly projectType: "external" | "configured"; + readonly languageServiceEnabled: boolean; + /** TypeScript version used by the server. */ + readonly version: string; + } + + export interface ProjectInfoTypeAcquisitionData { + readonly enable: boolean; + // Actual values of include/exclude entries are scrubbed. + readonly include: boolean; + readonly exclude: boolean; + } + + export interface FileStats { + readonly js: number; + readonly jsx: number; + readonly ts: number; + readonly tsx: number; + readonly dts: number; + } + + export type ProjectServiceEvent = ContextEvent | ConfigFileDiagEvent | ProjectLanguageServiceStateEvent | ProjectInfoTelemetryEvent; export interface ProjectServiceEventHandler { (event: ProjectServiceEvent): void; @@ -345,6 +391,9 @@ namespace ts.server { public readonly pluginProbeLocations: ReadonlyArray; public readonly allowLocalPluginLoads: boolean; + /** Tracks projects that we have already sent telemetry for. */ + private readonly seenProjects = createMap(); + constructor(opts: ProjectServiceOptions) { this.host = opts.host; this.logger = opts.logger; @@ -934,7 +983,10 @@ namespace ts.server { const projectOptions: ProjectOptions = { files: parsedCommandLine.fileNames, compilerOptions: parsedCommandLine.options, - configHasFilesProperty: config["files"] !== undefined, + configHasExtendsProperty: config.extends !== undefined, + configHasFilesProperty: config.files !== undefined, + configHasIncludeProperty: config.include !== undefined, + configHasExcludeProperty: config.exclude !== undefined, wildcardDirectories: createMapFromTemplate(parsedCommandLine.wildcardDirectories), typeAcquisition: parsedCommandLine.typeAcquisition, compileOnSave: parsedCommandLine.compileOnSave @@ -984,9 +1036,53 @@ namespace ts.server { this.addFilesToProjectAndUpdateGraph(project, files, externalFilePropertyReader, /*clientFileName*/ undefined, typeAcquisition, /*configFileErrors*/ undefined); this.externalProjects.push(project); + this.sendProjectTelemetry(project.externalProjectName, project); return project; } + private sendProjectTelemetry(projectKey: string, project: server.ExternalProject | server.ConfiguredProject, projectOptions?: ProjectOptions): void { + if (this.seenProjects.has(projectKey)) { + return; + } + this.seenProjects.set(projectKey, true); + + if (!this.eventHandler) return; + + const data: ProjectInfoTelemetryEventData = { + fileStats: countEachFileTypes(project.getScriptInfos()), + compilerOptions: convertCompilerOptionsForTelemetry(project.getCompilerOptions()), + typeAcquisition: convertTypeAcquisition(project.getTypeAcquisition()), + extends: projectOptions && projectOptions.configHasExtendsProperty, + files: projectOptions && projectOptions.configHasFilesProperty, + include: projectOptions && projectOptions.configHasIncludeProperty, + exclude: projectOptions && projectOptions.configHasExcludeProperty, + compileOnSave: project.compileOnSaveEnabled, + configFileName: configFileName(), + projectType: project instanceof server.ExternalProject ? "external" : "configured", + languageServiceEnabled: project.languageServiceEnabled, + version: ts.version, + }; + this.eventHandler({ eventName: ProjectInfoTelemetryEvent, data }); + + function configFileName(): ProjectInfoTelemetryEventData["configFileName"] { + if (!(project instanceof server.ConfiguredProject)) { + return "other"; + } + + const configFilePath = project instanceof server.ConfiguredProject && project.getConfigFilePath(); + const base = ts.getBaseFileName(configFilePath); + return base === "tsconfig.json" || base === "jsconfig.json" ? base : "other"; + } + + function convertTypeAcquisition({ enable, include, exclude }: TypeAcquisition): ProjectInfoTypeAcquisitionData { + return { + enable, + include: include !== undefined && include.length !== 0, + exclude: exclude !== undefined && exclude.length !== 0, + }; + } + } + private reportConfigFileDiagnostics(configFileName: string, diagnostics: Diagnostic[], triggerFile: string) { if (!this.eventHandler) { return; @@ -1020,6 +1116,7 @@ namespace ts.server { project.watchTypeRoots((project, path) => this.onTypeRootFileChanged(project, path)); this.configuredProjects.push(project); + this.sendProjectTelemetry(project.getConfigFilePath(), project, projectOptions); return project; } @@ -1052,7 +1149,7 @@ namespace ts.server { const conversionResult = this.convertConfigFileContentToProjectOptions(configFileName); const projectOptions: ProjectOptions = conversionResult.success ? conversionResult.projectOptions - : { files: [], compilerOptions: {}, typeAcquisition: { enable: false } }; + : { files: [], compilerOptions: {}, configHasExtendsProperty: false, configHasFilesProperty: false, configHasIncludeProperty: false, configHasExcludeProperty: false, typeAcquisition: { enable: false } }; const project = this.createAndAddConfiguredProject(configFileName, projectOptions, conversionResult.configFileErrors, clientFileName); return { success: conversionResult.success, diff --git a/src/server/project.ts b/src/server/project.ts index 7dc4388bf39..0646497acc5 100644 --- a/src/server/project.ts +++ b/src/server/project.ts @@ -13,7 +13,8 @@ namespace ts.server { External } - function countEachFileTypes(infos: ScriptInfo[]): { js: number, jsx: number, ts: number, tsx: number, dts: number } { + /* @internal */ + export function countEachFileTypes(infos: ScriptInfo[]): FileStats { const result = { js: 0, jsx: 0, ts: 0, tsx: 0, dts: 0 }; for (const info of infos) { switch (info.scriptKind) { @@ -730,6 +731,10 @@ namespace ts.server { } } + /** + * If a file is opened and no tsconfig (or jsconfig) is found, + * the file and its imports/references are put into an InferredProject. + */ export class InferredProject extends Project { private static newName = (() => { @@ -823,6 +828,11 @@ namespace ts.server { } } + /** + * If a file is opened, the server will look for a tsconfig (or jsconfig) + * and if successfull create a ConfiguredProject for it. + * Otherwise it will create an InferredProject. + */ export class ConfiguredProject extends Project { private typeAcquisition: TypeAcquisition; private projectFileWatcher: FileWatcher; @@ -1048,6 +1058,10 @@ namespace ts.server { } } + /** + * Project whose configuration is handled externally, such as in a '.csproj'. + * These are created only if a host explicitly calls `openExternalProject`. + */ export class ExternalProject extends Project { private typeAcquisition: TypeAcquisition; constructor(public externalProjectName: string, diff --git a/src/server/session.ts b/src/server/session.ts index 846607cd5ca..6ec234952db 100644 --- a/src/server/session.ts +++ b/src/server/session.ts @@ -337,13 +337,22 @@ namespace ts.server { const { triggerFile, configFileName, diagnostics } = event.data; this.configFileDiagnosticEvent(triggerFile, configFileName, diagnostics); break; - case ProjectLanguageServiceStateEvent: + case ProjectLanguageServiceStateEvent: { const eventName: protocol.ProjectLanguageServiceStateEventName = "projectLanguageServiceState"; this.event({ projectName: event.data.project.getProjectName(), languageServiceEnabled: event.data.languageServiceEnabled }, eventName); break; + } + case ProjectInfoTelemetryEvent: { + const eventName: protocol.TelemetryEventName = "telemetry"; + this.event({ + telemetryEventName: event.eventName, + payload: event.data, + }, eventName); + break; + } } } diff --git a/src/server/utilities.ts b/src/server/utilities.ts index ffc09f29ccd..093958b60c5 100644 --- a/src/server/utilities.ts +++ b/src/server/utilities.ts @@ -164,10 +164,13 @@ namespace ts.server { } export interface ProjectOptions { + configHasExtendsProperty: boolean; /** * true if config file explicitly listed files */ - configHasFilesProperty?: boolean; + configHasFilesProperty: boolean; + configHasIncludeProperty: boolean; + configHasExcludeProperty: boolean; /** * these fields can be present in the project file */ From 159614315cb44bef1bfd4af9529f51c45d56008b Mon Sep 17 00:00:00 2001 From: Mohamed Hegazy Date: Thu, 25 May 2017 13:23:00 -0700 Subject: [PATCH 19/56] Fix build breaks with the instrumenter --- Jakefile.js | 4 ++-- src/harness/instrumenter.ts | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/Jakefile.js b/Jakefile.js index 8ba4bd2f4e1..f1a714c1e26 100644 --- a/Jakefile.js +++ b/Jakefile.js @@ -1080,7 +1080,7 @@ var loggedIOJsPath = builtLocalDirectory + 'loggedIO.js'; file(loggedIOJsPath, [builtLocalDirectory, loggedIOpath], function () { var temp = builtLocalDirectory + 'temp'; jake.mkdirP(temp); - var options = "--types --outdir " + temp + ' ' + loggedIOpath; + var options = "--target es5 --lib es6 --types --outdir " + temp + ' ' + loggedIOpath; var cmd = host + " " + LKGDirectory + compilerFilename + " " + options + " "; console.log(cmd + "\n"); var ex = jake.createExec([cmd]); @@ -1094,7 +1094,7 @@ file(loggedIOJsPath, [builtLocalDirectory, loggedIOpath], function () { var instrumenterPath = harnessDirectory + 'instrumenter.ts'; var instrumenterJsPath = builtLocalDirectory + 'instrumenter.js'; -compileFile(instrumenterJsPath, [instrumenterPath], [tscFile, instrumenterPath].concat(libraryTargets), [], /*useBuiltCompiler*/ true); +compileFile(instrumenterJsPath, [instrumenterPath], [tscFile, instrumenterPath].concat(libraryTargets), [], /*useBuiltCompiler*/ true, { lib: "es6", types: ["node"] }); desc("Builds an instrumented tsc.js"); task('tsc-instrumented', [loggedIOJsPath, instrumenterJsPath, tscFile], function () { diff --git a/src/harness/instrumenter.ts b/src/harness/instrumenter.ts index b8f42e7e8bd..02aba0e7661 100644 --- a/src/harness/instrumenter.ts +++ b/src/harness/instrumenter.ts @@ -1,4 +1,3 @@ -declare const require: any, process: any; const fs: any = require("fs"); const path: any = require("path"); From cabe4d36060750d742a62f6cd3b27234ee83caf4 Mon Sep 17 00:00:00 2001 From: Yui T Date: Thu, 25 May 2017 19:49:04 -0700 Subject: [PATCH 20/56] Address PR --- src/compiler/binder.ts | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/src/compiler/binder.ts b/src/compiler/binder.ts index 8870757999f..80bdeae6df5 100644 --- a/src/compiler/binder.ts +++ b/src/compiler/binder.ts @@ -2178,11 +2178,10 @@ namespace ts { case SyntaxKind.JSDocRecordMember: return bindPropertyWorker(node as JSDocRecordMember); case SyntaxKind.JSDocPropertyTag: - let optionalType = 0; - if ((node as JSDocPropertyTag).typeExpression.type.kind === SyntaxKind.JSDocOptionalType) { - optionalType = SymbolFlags.Optional; - } - return declareSymbolAndAddToSymbolTable(node as JSDocPropertyTag, SymbolFlags.Property | optionalType, SymbolFlags.PropertyExcludes); + return declareSymbolAndAddToSymbolTable(node as JSDocPropertyTag, + (node as JSDocPropertyTag).typeExpression && (node as JSDocPropertyTag).typeExpression.type.kind === SyntaxKind.JSDocOptionalType ? + SymbolFlags.Property | SymbolFlags.Optional : SymbolFlags.Property, + SymbolFlags.PropertyExcludes); case SyntaxKind.JSDocFunctionType: return bindFunctionOrConstructorType(node); case SyntaxKind.JSDocTypeLiteral: From 4f791040fc7fa467dec2ae66bf9b0cc1b688e5e8 Mon Sep 17 00:00:00 2001 From: Yui T Date: Thu, 25 May 2017 20:16:52 -0700 Subject: [PATCH 21/56] Add tests and baselines --- .../reference/checkJsdocTypedefInParamTag1.js | 24 +++++++++++++++++++ .../checkJsdocTypedefInParamTag1.symbols | 17 +++++++++++++ .../checkJsdocTypedefInParamTag1.types | 20 ++++++++++++++++ .../jsdoc/checkJsdocTypedefInParamTag1.ts | 15 ++++++++++++ 4 files changed, 76 insertions(+) create mode 100644 tests/baselines/reference/checkJsdocTypedefInParamTag1.js create mode 100644 tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols create mode 100644 tests/baselines/reference/checkJsdocTypedefInParamTag1.types create mode 100644 tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js new file mode 100644 index 00000000000..28d6a96b3f9 --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js @@ -0,0 +1,24 @@ +//// [0.js] +// @ts-check +/** + * @typedef {Object} Opts + * @property {string} x + * @property {string=} y + * + * @param {Opts} opts + */ +function foo(opts) {} + +foo({x: 'abc'}); + +//// [0.js] +// @ts-check +/** + * @typedef {Object} Opts + * @property {string} x + * @property {string=} y + * + * @param {Opts} opts + */ +function foo(opts) { } +foo({ x: 'abc' }); diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols new file mode 100644 index 00000000000..19672d6e52c --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols @@ -0,0 +1,17 @@ +=== tests/cases/conformance/jsdoc/0.js === +// @ts-check +/** + * @typedef {Object} Opts + * @property {string} x + * @property {string=} y + * + * @param {Opts} opts + */ +function foo(opts) {} +>foo : Symbol(foo, Decl(0.js, 0, 0)) +>opts : Symbol(opts, Decl(0.js, 8, 13)) + +foo({x: 'abc'}); +>foo : Symbol(foo, Decl(0.js, 0, 0)) +>x : Symbol(x, Decl(0.js, 10, 5)) + diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types new file mode 100644 index 00000000000..ff30e8da8a8 --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types @@ -0,0 +1,20 @@ +=== tests/cases/conformance/jsdoc/0.js === +// @ts-check +/** + * @typedef {Object} Opts + * @property {string} x + * @property {string=} y + * + * @param {Opts} opts + */ +function foo(opts) {} +>foo : (opts: { x: string; y?: string; }) => void +>opts : { x: string; y?: string; } + +foo({x: 'abc'}); +>foo({x: 'abc'}) : void +>foo : (opts: { x: string; y?: string; }) => void +>{x: 'abc'} : { x: string; } +>x : string +>'abc' : "abc" + diff --git a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts new file mode 100644 index 00000000000..261ce070cf2 --- /dev/null +++ b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts @@ -0,0 +1,15 @@ +// @allowJS: true +// @suppressOutputPathCheck: true + +// @filename: 0.js +// @ts-check +/** + * @typedef {Object} Opts + * @property {string} x + * @property {string=} y + * + * @param {Opts} opts + */ +function foo(opts) {} + +foo({x: 'abc'}); \ No newline at end of file From 23be471def7c30dd5b2ce7959986b2259c7fb723 Mon Sep 17 00:00:00 2001 From: Yui T Date: Thu, 25 May 2017 21:52:23 -0700 Subject: [PATCH 22/56] Fix linting --- src/compiler/binder.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/compiler/binder.ts b/src/compiler/binder.ts index 80bdeae6df5..ec3e8157589 100644 --- a/src/compiler/binder.ts +++ b/src/compiler/binder.ts @@ -1,4 +1,4 @@ -/// +/// /// /* @internal */ @@ -3596,4 +3596,4 @@ namespace ts { return TransformFlags.NodeExcludes; } } -} +} \ No newline at end of file From d68038ad28d482e38626e487c22a264295dfa8de Mon Sep 17 00:00:00 2001 From: Yui T Date: Thu, 25 May 2017 22:34:48 -0700 Subject: [PATCH 23/56] Support bracket for optional property --- src/compiler/binder.ts | 2 +- src/compiler/parser.ts | 17 ++++++++++++----- src/compiler/types.ts | 1 + 3 files changed, 14 insertions(+), 6 deletions(-) diff --git a/src/compiler/binder.ts b/src/compiler/binder.ts index ec3e8157589..d55f3650c10 100644 --- a/src/compiler/binder.ts +++ b/src/compiler/binder.ts @@ -2179,7 +2179,7 @@ namespace ts { return bindPropertyWorker(node as JSDocRecordMember); case SyntaxKind.JSDocPropertyTag: return declareSymbolAndAddToSymbolTable(node as JSDocPropertyTag, - (node as JSDocPropertyTag).typeExpression && (node as JSDocPropertyTag).typeExpression.type.kind === SyntaxKind.JSDocOptionalType ? + (node as JSDocPropertyTag).isBracketed || ((node as JSDocPropertyTag).typeExpression && (node as JSDocPropertyTag).typeExpression.type.kind === SyntaxKind.JSDocOptionalType) ? SymbolFlags.Property | SymbolFlags.Optional : SymbolFlags.Property, SymbolFlags.PropertyExcludes); case SyntaxKind.JSDocFunctionType: diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 04209ab0924..07d4a9ada41 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6631,10 +6631,7 @@ namespace ts { }); } - function parseParamTag(atToken: AtToken, tagName: Identifier) { - let typeExpression = tryParseTypeExpression(); - skipWhitespace(); - + function parseBracketNameInPropertyAndParamTag() { let name: Identifier; let isBracketed: boolean; // Looking for something like '[foo]' or 'foo' @@ -6653,6 +6650,14 @@ namespace ts { else if (tokenIsIdentifierOrKeyword(token())) { name = parseJSDocIdentifierName(); } + return { name, isBracketed }; + } + + function parseParamTag(atToken: AtToken, tagName: Identifier) { + let typeExpression = tryParseTypeExpression(); + skipWhitespace(); + + const { name, isBracketed } = parseBracketNameInPropertyAndParamTag(); if (!name) { parseErrorAtPosition(scanner.getStartPos(), 0, Diagnostics.Identifier_expected); @@ -6709,8 +6714,9 @@ namespace ts { function parsePropertyTag(atToken: AtToken, tagName: Identifier): JSDocPropertyTag { const typeExpression = tryParseTypeExpression(); skipWhitespace(); - const name = parseJSDocIdentifierName(); + const { name, isBracketed } = parseBracketNameInPropertyAndParamTag(); skipWhitespace(); + if (!name) { parseErrorAtPosition(scanner.getStartPos(), /*length*/ 0, Diagnostics.Identifier_expected); return undefined; @@ -6721,6 +6727,7 @@ namespace ts { result.tagName = tagName; result.name = name; result.typeExpression = typeExpression; + result.isBracketed = isBracketed; return finishNode(result); } diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 73a2e46be90..93098993754 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -2143,6 +2143,7 @@ namespace ts { kind: SyntaxKind.JSDocPropertyTag; name: Identifier; typeExpression: JSDocTypeExpression; + isBracketed: boolean; } export interface JSDocTypeLiteral extends JSDocType { From 8ae2fbadd0a82a3a77e11a066bc0318e2129e480 Mon Sep 17 00:00:00 2001 From: Yui T Date: Thu, 25 May 2017 22:35:15 -0700 Subject: [PATCH 24/56] Add tests and baselines --- tests/baselines/reference/checkJsdocTypedefInParamTag1.js | 4 ++++ .../reference/checkJsdocTypedefInParamTag1.symbols | 6 ++++-- .../reference/checkJsdocTypedefInParamTag1.types | 8 +++++--- .../conformance/jsdoc/checkJsdocTypedefInParamTag1.ts | 2 ++ 4 files changed, 15 insertions(+), 5 deletions(-) diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js index 28d6a96b3f9..d4983bfd581 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js @@ -4,6 +4,8 @@ * @typedef {Object} Opts * @property {string} x * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] * * @param {Opts} opts */ @@ -17,6 +19,8 @@ foo({x: 'abc'}); * @typedef {Object} Opts * @property {string} x * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] * * @param {Opts} opts */ diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols index 19672d6e52c..cd2455797b4 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols @@ -4,14 +4,16 @@ * @typedef {Object} Opts * @property {string} x * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] * * @param {Opts} opts */ function foo(opts) {} >foo : Symbol(foo, Decl(0.js, 0, 0)) ->opts : Symbol(opts, Decl(0.js, 8, 13)) +>opts : Symbol(opts, Decl(0.js, 10, 13)) foo({x: 'abc'}); >foo : Symbol(foo, Decl(0.js, 0, 0)) ->x : Symbol(x, Decl(0.js, 10, 5)) +>x : Symbol(x, Decl(0.js, 12, 5)) diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types index ff30e8da8a8..cc923e33030 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types @@ -4,16 +4,18 @@ * @typedef {Object} Opts * @property {string} x * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] * * @param {Opts} opts */ function foo(opts) {} ->foo : (opts: { x: string; y?: string; }) => void ->opts : { x: string; y?: string; } +>foo : (opts: { x: string; y?: string; z?: string; w?: string; }) => void +>opts : { x: string; y?: string; z?: string; w?: string; } foo({x: 'abc'}); >foo({x: 'abc'}) : void ->foo : (opts: { x: string; y?: string; }) => void +>foo : (opts: { x: string; y?: string; z?: string; w?: string; }) => void >{x: 'abc'} : { x: string; } >x : string >'abc' : "abc" diff --git a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts index 261ce070cf2..80ca21bd4ff 100644 --- a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts +++ b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts @@ -7,6 +7,8 @@ * @typedef {Object} Opts * @property {string} x * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] * * @param {Opts} opts */ From 2412f8c6cfaadd769af9d81a813c60c7c0768fa4 Mon Sep 17 00:00:00 2001 From: Andy Date: Fri, 26 May 2017 07:06:11 -0700 Subject: [PATCH 25/56] Allow configurable npmLocation for typingsInstaller (#16084) * Allow configurable npmLocation for typingsInstaller * Undo "export class" changes * Add log for npmLocation * Log whether '--npmLocation' was provided --- src/server/server.ts | 36 +++++++++++-------- src/server/shared.ts | 7 +++- .../typingsInstaller/nodeTypingsInstaller.ts | 11 +++--- 3 files changed, 34 insertions(+), 20 deletions(-) diff --git a/src/server/server.ts b/src/server/server.ts index ed3e2dd8207..390a0f2f6f4 100644 --- a/src/server/server.ts +++ b/src/server/server.ts @@ -13,6 +13,7 @@ namespace ts.server { globalTypingsCacheLocation: string; logger: Logger; typingSafeListLocation: string; + npmLocation: string | undefined; telemetryEnabled: boolean; globalPlugins: string[]; pluginProbeLocations: string[]; @@ -234,6 +235,7 @@ namespace ts.server { eventPort: number, readonly globalTypingsCacheLocation: string, readonly typingSafeListLocation: string, + private readonly npmLocation: string | undefined, private newLine: string) { this.throttledOperations = new ThrottledOperations(host); if (eventPort) { @@ -278,19 +280,21 @@ namespace ts.server { if (this.typingSafeListLocation) { args.push(Arguments.TypingSafeListLocation, this.typingSafeListLocation); } + if (this.npmLocation) { + args.push(Arguments.NpmLocation, this.npmLocation); + } + const execArgv: string[] = []; - { - for (const arg of process.execArgv) { - const match = /^--(debug|inspect)(=(\d+))?$/.exec(arg); - if (match) { - // if port is specified - use port + 1 - // otherwise pick a default port depending on if 'debug' or 'inspect' and use its value + 1 - const currentPort = match[3] !== undefined - ? +match[3] - : match[1] === "debug" ? 5858 : 9229; - execArgv.push(`--${match[1]}=${currentPort + 1}`); - break; - } + for (const arg of process.execArgv) { + const match = /^--(debug|inspect)(=(\d+))?$/.exec(arg); + if (match) { + // if port is specified - use port + 1 + // otherwise pick a default port depending on if 'debug' or 'inspect' and use its value + 1 + const currentPort = match[3] !== undefined + ? +match[3] + : match[1] === "debug" ? 5858 : 9229; + execArgv.push(`--${match[1]}=${currentPort + 1}`); + break; } } @@ -389,10 +393,10 @@ namespace ts.server { class IOSession extends Session { constructor(options: IOSessionOptions) { - const { host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, canUseEvents } = options; + const { host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, npmLocation, canUseEvents } = options; const typingsInstaller = disableAutomaticTypingAcquisition ? undefined - : new NodeTypingsInstaller(telemetryEnabled, logger, host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, host.newLine); + : new NodeTypingsInstaller(telemetryEnabled, logger, host, installerEventPort, globalTypingsCacheLocation, typingSafeListLocation, npmLocation, host.newLine); super({ host, @@ -741,7 +745,8 @@ namespace ts.server { validateLocaleAndSetLanguage(localeStr, sys); } - const typingSafeListLocation = findArgument("--typingSafeListLocation"); + const typingSafeListLocation = findArgument(Arguments.TypingSafeListLocation); + const npmLocation = findArgument(Arguments.NpmLocation); const globalPlugins = (findArgument("--globalPlugins") || "").split(","); const pluginProbeLocations = (findArgument("--pluginProbeLocations") || "").split(","); @@ -760,6 +765,7 @@ namespace ts.server { disableAutomaticTypingAcquisition, globalTypingsCacheLocation: getGlobalTypingsCacheLocation(), typingSafeListLocation, + npmLocation, telemetryEnabled, logger, globalPlugins, diff --git a/src/server/shared.ts b/src/server/shared.ts index 6dcf8881927..1285eba06e1 100644 --- a/src/server/shared.ts +++ b/src/server/shared.ts @@ -12,13 +12,18 @@ namespace ts.server { export const LogFile = "--logFile"; export const EnableTelemetry = "--enableTelemetry"; export const TypingSafeListLocation = "--typingSafeListLocation"; + /** + * This argument specifies the location of the NPM executable. + * typingsInstaller will run the command with `${npmLocation} install ...`. + */ + export const NpmLocation = "--npmLocation"; } export function hasArgument(argumentName: string) { return sys.args.indexOf(argumentName) >= 0; } - export function findArgument(argumentName: string) { + export function findArgument(argumentName: string): string | undefined { const index = sys.args.indexOf(argumentName); return index >= 0 && index < sys.args.length - 1 ? sys.args[index + 1] diff --git a/src/server/typingsInstaller/nodeTypingsInstaller.ts b/src/server/typingsInstaller/nodeTypingsInstaller.ts index 1182450ce81..797962cba08 100644 --- a/src/server/typingsInstaller/nodeTypingsInstaller.ts +++ b/src/server/typingsInstaller/nodeTypingsInstaller.ts @@ -30,7 +30,8 @@ namespace ts.server.typingsInstaller { } } - function getNPMLocation(processName: string) { + /** Used if `--npmLocation` is not passed. */ + function getDefaultNPMLocation(processName: string) { if (path.basename(processName).indexOf("node") === 0) { return `"${path.join(path.dirname(process.argv[0]), "npm")}"`; } @@ -76,17 +77,18 @@ namespace ts.server.typingsInstaller { private delayedInitializationError: InitializationFailedResponse; - constructor(globalTypingsCacheLocation: string, typingSafeListLocation: string, throttleLimit: number, log: Log) { + constructor(globalTypingsCacheLocation: string, typingSafeListLocation: string, npmLocation: string | undefined, throttleLimit: number, log: Log) { super( sys, globalTypingsCacheLocation, typingSafeListLocation ? toPath(typingSafeListLocation, "", createGetCanonicalFileName(sys.useCaseSensitiveFileNames)) : toPath("typingSafeList.json", __dirname, createGetCanonicalFileName(sys.useCaseSensitiveFileNames)), throttleLimit, log); + this.npmPath = npmLocation !== undefined ? npmLocation : getDefaultNPMLocation(process.argv[0]); if (this.log.isEnabled()) { this.log.writeLine(`Process id: ${process.pid}`); + this.log.writeLine(`NPM location: ${this.npmPath} (explicit '${Arguments.NpmLocation}' ${npmLocation === undefined ? "not " : ""} provided)`); } - this.npmPath = getNPMLocation(process.argv[0]); ({ execSync: this.execSync } = require("child_process")); this.ensurePackageDirectoryExists(globalTypingsCacheLocation); @@ -168,6 +170,7 @@ namespace ts.server.typingsInstaller { const logFilePath = findArgument(server.Arguments.LogFile); const globalTypingsCacheLocation = findArgument(server.Arguments.GlobalCacheLocation); const typingSafeListLocation = findArgument(server.Arguments.TypingSafeListLocation); + const npmLocation = findArgument(server.Arguments.NpmLocation); const log = new FileLog(logFilePath); if (log.isEnabled()) { @@ -181,6 +184,6 @@ namespace ts.server.typingsInstaller { } process.exit(0); }); - const installer = new NodeTypingsInstaller(globalTypingsCacheLocation, typingSafeListLocation, /*throttleLimit*/5, log); + const installer = new NodeTypingsInstaller(globalTypingsCacheLocation, typingSafeListLocation, npmLocation, /*throttleLimit*/5, log); installer.listen(); } \ No newline at end of file From 6972766e917956d2f9c148af58d484f7d2ed1da2 Mon Sep 17 00:00:00 2001 From: Ika Date: Sat, 27 May 2017 00:28:56 +0800 Subject: [PATCH 26/56] Add missing undefined type for createProperty initializer (#16095) --- src/compiler/factory.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/compiler/factory.ts b/src/compiler/factory.ts index 2b41f13f8a4..943d011c350 100644 --- a/src/compiler/factory.ts +++ b/src/compiler/factory.ts @@ -303,7 +303,7 @@ namespace ts { : node; } - export function createProperty(decorators: Decorator[] | undefined, modifiers: Modifier[] | undefined, name: string | PropertyName, questionToken: QuestionToken | undefined, type: TypeNode | undefined, initializer: Expression) { + export function createProperty(decorators: Decorator[] | undefined, modifiers: Modifier[] | undefined, name: string | PropertyName, questionToken: QuestionToken | undefined, type: TypeNode | undefined, initializer: Expression | undefined) { const node = createSynthesizedNode(SyntaxKind.PropertyDeclaration); node.decorators = asNodeArray(decorators); node.modifiers = asNodeArray(modifiers); @@ -314,7 +314,7 @@ namespace ts { return node; } - export function updateProperty(node: PropertyDeclaration, decorators: Decorator[] | undefined, modifiers: Modifier[] | undefined, name: PropertyName, type: TypeNode | undefined, initializer: Expression) { + export function updateProperty(node: PropertyDeclaration, decorators: Decorator[] | undefined, modifiers: Modifier[] | undefined, name: PropertyName, type: TypeNode | undefined, initializer: Expression | undefined) { return node.decorators !== decorators || node.modifiers !== modifiers || node.name !== name From 3cd9f3d2d4afc1c817ea53b3e40d9598197e9aaa Mon Sep 17 00:00:00 2001 From: Andy Date: Fri, 26 May 2017 09:52:46 -0700 Subject: [PATCH 27/56] Support services for @typedef (#16087) * Support services for @typedef * Ensure JSDocTypeReference has SemanticMeaning.Type * Get SemanticMeaning right --- src/compiler/types.ts | 3 ++ src/compiler/utilities.ts | 12 +++++++ src/services/findAllReferences.ts | 3 +- src/services/goToDefinition.ts | 2 +- src/services/utilities.ts | 32 +++++++++++++------ .../jsdocTypedefTagSemanticMeaning0.ts | 16 ++++++++++ .../jsdocTypedefTagSemanticMeaning1.ts | 12 +++++++ .../fourslash/jsdocTypedefTagServices.ts | 28 ++++++++++++++++ 8 files changed, 97 insertions(+), 11 deletions(-) create mode 100644 tests/cases/fourslash/jsdocTypedefTagSemanticMeaning0.ts create mode 100644 tests/cases/fourslash/jsdocTypedefTagSemanticMeaning1.ts create mode 100644 tests/cases/fourslash/jsdocTypedefTagServices.ts diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 73a2e46be90..c295a4c9563 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -2102,6 +2102,7 @@ namespace ts { } export interface JSDocTag extends Node { + parent: JSDoc; atToken: AtToken; tagName: Identifier; comment: string | undefined; @@ -2132,6 +2133,7 @@ namespace ts { } export interface JSDocTypedefTag extends JSDocTag, NamedDeclaration { + parent: JSDoc; kind: SyntaxKind.JSDocTypedefTag; fullName?: JSDocNamespaceDeclaration | Identifier; name?: Identifier; @@ -2140,6 +2142,7 @@ namespace ts { } export interface JSDocPropertyTag extends JSDocTag, TypeElement { + parent: JSDoc; kind: SyntaxKind.JSDocPropertyTag; name: Identifier; typeExpression: JSDocTypeExpression; diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 22210419af7..134404c247b 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -288,6 +288,14 @@ namespace ts { return node.kind >= SyntaxKind.FirstJSDocNode && node.kind <= SyntaxKind.LastJSDocNode; } + export function isJSDoc(node: Node): node is JSDoc { + return node.kind === SyntaxKind.JSDocComment; + } + + export function isJSDocTypedefTag(node: Node): node is JSDocTypedefTag { + return node.kind === SyntaxKind.JSDocTypedefTag; + } + export function isJSDocTag(node: Node) { return node.kind >= SyntaxKind.FirstJSDocTagNode && node.kind <= SyntaxKind.LastJSDocTagNode; } @@ -1551,6 +1559,10 @@ namespace ts { } export function getJSDocs(node: Node): (JSDoc | JSDocTag)[] { + if (isJSDocTypedefTag(node)) { + return [node.parent]; + } + let cache: (JSDoc | JSDocTag)[] = node.jsDocCache; if (!cache) { getJSDocsWorker(node); diff --git a/src/services/findAllReferences.ts b/src/services/findAllReferences.ts index 7877e28b6fc..df499cbd38a 100644 --- a/src/services/findAllReferences.ts +++ b/src/services/findAllReferences.ts @@ -784,7 +784,8 @@ namespace ts.FindAllReferences.Core { return; } - for (const position of getPossibleSymbolReferencePositions(sourceFile, search.text, container, /*fullStart*/ state.options.findInComments || container.jsDoc !== undefined)) { + const fullStart = state.options.findInComments || container.jsDoc !== undefined || forEach(search.symbol.declarations, d => d.kind === ts.SyntaxKind.JSDocTypedefTag); + for (const position of getPossibleSymbolReferencePositions(sourceFile, search.text, container, fullStart)) { getReferencesAtLocation(sourceFile, position, search, state); } } diff --git a/src/services/goToDefinition.ts b/src/services/goToDefinition.ts index 9b96f339bf6..ac60ba7942c 100644 --- a/src/services/goToDefinition.ts +++ b/src/services/goToDefinition.ts @@ -8,7 +8,7 @@ namespace ts.GoToDefinition { if (referenceFile) { return [getDefinitionInfoForFileReference(comment.fileName, referenceFile.fileName)]; } - return undefined; + // Might still be on jsdoc, so keep looking. } // Type reference directives diff --git a/src/services/utilities.ts b/src/services/utilities.ts index 2e771a73286..7a87c0939c7 100644 --- a/src/services/utilities.ts +++ b/src/services/utilities.ts @@ -39,13 +39,14 @@ namespace ts { case SyntaxKind.TypeLiteral: return SemanticMeaning.Type; + case SyntaxKind.JSDocTypedefTag: + // If it has no name node, it shares the name with the value declaration below it. + return (node as JSDocTypedefTag).name === undefined ? SemanticMeaning.Value | SemanticMeaning.Type : SemanticMeaning.Type; + case SyntaxKind.EnumMember: case SyntaxKind.ClassDeclaration: return SemanticMeaning.Value | SemanticMeaning.Type; - case SyntaxKind.EnumDeclaration: - return SemanticMeaning.All; - case SyntaxKind.ModuleDeclaration: if (isAmbientModule(node)) { return SemanticMeaning.Namespace | SemanticMeaning.Value; @@ -57,6 +58,7 @@ namespace ts { return SemanticMeaning.Namespace; } + case SyntaxKind.EnumDeclaration: case SyntaxKind.NamedImports: case SyntaxKind.ImportSpecifier: case SyntaxKind.ImportEqualsDeclaration: @@ -70,7 +72,7 @@ namespace ts { return SemanticMeaning.Namespace | SemanticMeaning.Value; } - return SemanticMeaning.Value | SemanticMeaning.Type | SemanticMeaning.Namespace; + return SemanticMeaning.All; } export function getMeaningFromLocation(node: Node): SemanticMeaning { @@ -78,7 +80,7 @@ namespace ts { return SemanticMeaning.Value; } else if (node.parent.kind === SyntaxKind.ExportAssignment) { - return SemanticMeaning.Value | SemanticMeaning.Type | SemanticMeaning.Namespace; + return SemanticMeaning.All; } else if (isInRightSideOfImport(node)) { return getMeaningFromRightHandSideOfImportEquals(node); @@ -162,10 +164,22 @@ namespace ts { node = node.parent; } - return node.parent.kind === SyntaxKind.TypeReference || - (node.parent.kind === SyntaxKind.ExpressionWithTypeArguments && !isExpressionWithTypeArgumentsInClassExtendsClause(node.parent)) || - (node.kind === SyntaxKind.ThisKeyword && !isPartOfExpression(node)) || - node.kind === SyntaxKind.ThisType; + switch (node.kind) { + case SyntaxKind.ThisKeyword: + return !isPartOfExpression(node); + case SyntaxKind.ThisType: + return true; + } + + switch (node.parent.kind) { + case SyntaxKind.TypeReference: + case SyntaxKind.JSDocTypeReference: + return true; + case SyntaxKind.ExpressionWithTypeArguments: + return !isExpressionWithTypeArgumentsInClassExtendsClause(node.parent); + } + + return false; } export function isCallExpressionTarget(node: Node): boolean { diff --git a/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning0.ts b/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning0.ts new file mode 100644 index 00000000000..3673c86b381 --- /dev/null +++ b/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning0.ts @@ -0,0 +1,16 @@ +/// + +// @allowJs: true +// @Filename: a.js + +/////** @typedef {number} [|{| "isWriteAccess": true, "isDefinition": true |}T|] */ + +////const [|{| "isWriteAccess": true, "isDefinition": true |}T|] = 1; + +/////** @type {[|T|]} */ +////const n = [|T|]; + +const [t0, v0, t1, v1] = test.ranges(); + +verify.singleReferenceGroup("type T = number\nconst T: 1", [t0, t1]); +verify.singleReferenceGroup("type T = number\nconst T: 1", [v0, v1]); diff --git a/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning1.ts b/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning1.ts new file mode 100644 index 00000000000..f052d4bd870 --- /dev/null +++ b/tests/cases/fourslash/jsdocTypedefTagSemanticMeaning1.ts @@ -0,0 +1,12 @@ +/// + +// @allowJs: true +// @Filename: a.js + +/////** @typedef {number} */ +////const [|{| "isWriteAccess": true, "isDefinition": true |}T|] = 1; + +/////** @type {[|T|]} */ +////const n = [|T|]; + +verify.singleReferenceGroup("type T = number\nconst T: 1"); diff --git a/tests/cases/fourslash/jsdocTypedefTagServices.ts b/tests/cases/fourslash/jsdocTypedefTagServices.ts new file mode 100644 index 00000000000..c97707e4d25 --- /dev/null +++ b/tests/cases/fourslash/jsdocTypedefTagServices.ts @@ -0,0 +1,28 @@ +/// + +// @allowJs: true +// @Filename: a.js + +/////** +//// * Doc comment +//// * @typedef /*def*/[|{| "isWriteAccess": true, "isDefinition": true |}Product|] +//// * @property {string} title +//// */ + +/////** +//// * @type {/*use*/[|Product|]} +//// */ +////const product = null; + +const desc = `type Product = { + title: string; +}`; + +verify.quickInfoAt("use", desc, "Doc comment"); + +verify.goToDefinition("use", "def"); + +verify.rangesAreOccurrences(); +verify.rangesAreDocumentHighlights(); +verify.singleReferenceGroup(desc); +verify.rangesAreRenameLocations(); From 7ca91f86a7960d5464de669f71ec8d950c63f4fc Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Fri, 26 May 2017 10:44:11 -0700 Subject: [PATCH 28/56] Address CR feedback --- src/compiler/checker.ts | 33 +++++++++++++++------------------ 1 file changed, 15 insertions(+), 18 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 30100332210..91ee22471aa 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10292,29 +10292,26 @@ namespace ts { // Because the anyFunctionType is internal, it should not be exposed to the user by adding // it as an inference candidate. Hopefully, a better candidate will come along that does // not contain anyFunctionType when we come back to this argument for its second round - // of inference. + // of inference. Also, we exclude inferences for silentNeverType which is used as a wildcard + // when constructing types from type parameters that had no inference candidates. if (source.flags & TypeFlags.ContainsAnyFunctionType || source === silentNeverType) { return; } - for (const inference of inferences) { - if (target === inference.typeParameter) { - // Even if an inference is marked as fixed, we can add candidates from inferences made - // from the return type of generic functions (which only happens when no other candidates - // are present). - if (!inference.isFixed) { - if (!inference.candidates || priority < inference.priority) { - inference.candidates = [source]; - inference.priority = priority; - } - else if (priority === inference.priority) { - inference.candidates.push(source); - } - if (!(priority & InferencePriority.ReturnType) && target.flags & TypeFlags.TypeParameter && !isTypeParameterAtTopLevel(originalTarget, target)) { - inference.topLevel = false; - } + const inference = getInferenceInfoForType(target); + if (inference) { + if (!inference.isFixed) { + if (!inference.candidates || priority < inference.priority) { + inference.candidates = [source]; + inference.priority = priority; + } + else if (priority === inference.priority) { + inference.candidates.push(source); + } + if (!(priority & InferencePriority.ReturnType) && target.flags & TypeFlags.TypeParameter && !isTypeParameterAtTopLevel(originalTarget, target)) { + inference.topLevel = false; } - return; } + return; } } else if (getObjectFlags(source) & ObjectFlags.Reference && getObjectFlags(target) & ObjectFlags.Reference && (source).target === (target).target) { From 0cbfc79ca7f0a43b8be3190ce363f3746184adbe Mon Sep 17 00:00:00 2001 From: Yui T Date: Fri, 26 May 2017 11:20:57 -0700 Subject: [PATCH 29/56] Rename test files to be more consistent and move them into jsdoc folder --- .../conformance/jsdoc/checkJsdocParamTag1.ts | 14 +++++++++++ .../conformance/jsdoc/checkJsdocReturnTag1.ts | 25 +++++++++++++++++++ .../conformance/jsdoc/checkJsdocReturnTag2.ts | 18 +++++++++++++ .../checkJsdocTypeTag1.ts} | 7 ++++++ .../checkJsdocTypeTag2.ts} | 11 +++++++- .../conformance/jsdoc/jsdocReturnTag1.ts | 23 +++++++++++++++++ .../jsDocTypes.ts => jsdoc/jsdocTypeTag.ts} | 4 ++- tests/cases/conformance/jsdoc/returns.ts | 9 ------- 8 files changed, 100 insertions(+), 11 deletions(-) create mode 100644 tests/cases/conformance/jsdoc/checkJsdocParamTag1.ts create mode 100644 tests/cases/conformance/jsdoc/checkJsdocReturnTag1.ts create mode 100644 tests/cases/conformance/jsdoc/checkJsdocReturnTag2.ts rename tests/cases/conformance/{salsa/jsDocTypes2.ts => jsdoc/checkJsdocTypeTag1.ts} (74%) rename tests/cases/conformance/{salsa/jsDocTypes3.ts => jsdoc/checkJsdocTypeTag2.ts} (57%) create mode 100644 tests/cases/conformance/jsdoc/jsdocReturnTag1.ts rename tests/cases/conformance/{salsa/jsDocTypes.ts => jsdoc/jsdocTypeTag.ts} (87%) delete mode 100644 tests/cases/conformance/jsdoc/returns.ts diff --git a/tests/cases/conformance/jsdoc/checkJsdocParamTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocParamTag1.ts new file mode 100644 index 00000000000..1586a10472c --- /dev/null +++ b/tests/cases/conformance/jsdoc/checkJsdocParamTag1.ts @@ -0,0 +1,14 @@ +// @allowJS: true +// @suppressOutputPathCheck: true + +// @filename: 0.js +// @ts-check +/** + * @param {number=} n + * @param {string} [s] + */ +function foo(n, s) {} + +foo(); +foo(1); +foo(1, "hi"); \ No newline at end of file diff --git a/tests/cases/conformance/jsdoc/checkJsdocReturnTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocReturnTag1.ts new file mode 100644 index 00000000000..fde7c3fa0f4 --- /dev/null +++ b/tests/cases/conformance/jsdoc/checkJsdocReturnTag1.ts @@ -0,0 +1,25 @@ +// @allowJs: true +// @out: dummy.js + +// @filename: returns.js +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return "hello"; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return "hello world"; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} \ No newline at end of file diff --git a/tests/cases/conformance/jsdoc/checkJsdocReturnTag2.ts b/tests/cases/conformance/jsdoc/checkJsdocReturnTag2.ts new file mode 100644 index 00000000000..02b7fbeacef --- /dev/null +++ b/tests/cases/conformance/jsdoc/checkJsdocReturnTag2.ts @@ -0,0 +1,18 @@ +// @allowJs: true +// @out: dummy.js + +// @filename: returns.js +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} + +/** + * @returns {string | number} This comment is not currently exposed + */ +function f1() { + return 5 || true; +} \ No newline at end of file diff --git a/tests/cases/conformance/salsa/jsDocTypes2.ts b/tests/cases/conformance/jsdoc/checkJsdocTypeTag1.ts similarity index 74% rename from tests/cases/conformance/salsa/jsDocTypes2.ts rename to tests/cases/conformance/jsdoc/checkJsdocTypeTag1.ts index 612804b91d7..fe3ea76cfc1 100644 --- a/tests/cases/conformance/salsa/jsDocTypes2.ts +++ b/tests/cases/conformance/jsdoc/checkJsdocTypeTag1.ts @@ -3,8 +3,15 @@ // @filename: 0.js // @ts-check +/** @type {String} */ +var S = "hello world"; + +/** @type {number} */ +var n = 10; + /** @type {*} */ var anyT = 2; +anyT = "hello"; /** @type {?} */ var anyT1 = 2; diff --git a/tests/cases/conformance/salsa/jsDocTypes3.ts b/tests/cases/conformance/jsdoc/checkJsdocTypeTag2.ts similarity index 57% rename from tests/cases/conformance/salsa/jsDocTypes3.ts rename to tests/cases/conformance/jsdoc/checkJsdocTypeTag2.ts index bf207bca869..a7dffdb90a7 100644 --- a/tests/cases/conformance/salsa/jsDocTypes3.ts +++ b/tests/cases/conformance/jsdoc/checkJsdocTypeTag2.ts @@ -3,6 +3,11 @@ // @filename: 0.js // @ts-check +/** @type {String} */ +var S = true; + +/** @type {number} */ +var n = "hello"; /** @type {function (number)} */ const x1 = (a) => a + 1; @@ -13,4 +18,8 @@ const x2 = (a) => a + 1; /** @type {string} */ var a; -a = x2(0); \ No newline at end of file +a = x2(0); + +/** @type {function (number): number} */ +const x2 = (a) => a.concat("hi"); +x2(0); \ No newline at end of file diff --git a/tests/cases/conformance/jsdoc/jsdocReturnTag1.ts b/tests/cases/conformance/jsdoc/jsdocReturnTag1.ts new file mode 100644 index 00000000000..a425322a749 --- /dev/null +++ b/tests/cases/conformance/jsdoc/jsdocReturnTag1.ts @@ -0,0 +1,23 @@ +// @allowJs: true +// @filename: returns.js +// @out: dummy.js +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return 5; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} \ No newline at end of file diff --git a/tests/cases/conformance/salsa/jsDocTypes.ts b/tests/cases/conformance/jsdoc/jsdocTypeTag.ts similarity index 87% rename from tests/cases/conformance/salsa/jsDocTypes.ts rename to tests/cases/conformance/jsdoc/jsdocTypeTag.ts index 9a13c533d0a..d566c61e185 100644 --- a/tests/cases/conformance/salsa/jsDocTypes.ts +++ b/tests/cases/conformance/jsdoc/jsdocTypeTag.ts @@ -57,7 +57,8 @@ var nullable; /** @type {Object} */ var Obj; - +/** @type {Function} */ +var Func; // @filename: b.ts var S: string; @@ -78,3 +79,4 @@ var P: Promise; var p: Promise; var nullable: number | null; var Obj: any; +var Func: Function; diff --git a/tests/cases/conformance/jsdoc/returns.ts b/tests/cases/conformance/jsdoc/returns.ts deleted file mode 100644 index 72cb4a6cb67..00000000000 --- a/tests/cases/conformance/jsdoc/returns.ts +++ /dev/null @@ -1,9 +0,0 @@ -// @allowJs: true -// @filename: returns.js -// @out: dummy.js -/** - * @returns {string} This comment is not currently exposed - */ -function f() { - return ""; -} From e82e73753dac025933e37218469dfdf414c3c14d Mon Sep 17 00:00:00 2001 From: Yui T Date: Fri, 26 May 2017 11:21:06 -0700 Subject: [PATCH 30/56] Update baselines --- .../reference/checkJsdocParamTag1.js | 22 +++ .../reference/checkJsdocParamTag1.symbols | 20 +++ .../reference/checkJsdocParamTag1.types | 26 ++++ .../reference/checkJsdocReturnTag1.js | 43 ++++++ .../reference/checkJsdocReturnTag1.symbols | 28 ++++ .../reference/checkJsdocReturnTag1.types | 33 ++++ .../reference/checkJsdocReturnTag2.js | 30 ++++ .../reference/checkJsdocReturnTag2.symbols | 19 +++ .../reference/checkJsdocReturnTag2.types | 23 +++ .../{jsDocTypes2.js => checkJsdocTypeTag1.js} | 12 ++ .../reference/checkJsdocTypeTag1.symbols | 51 +++++++ ...cTypes2.types => checkJsdocTypeTag1.types} | 17 ++- .../reference/checkJsdocTypeTag2.errors.txt | 42 ++++++ .../baselines/reference/checkJsdocTypeTag2.js | 40 +++++ ...rors.txt => checkJsdocTypeTag3.errors.txt} | 6 +- .../{jsDocTypes3.js => checkJsdocTypeTag3.js} | 0 tests/baselines/reference/jsDocTypes2.symbols | 40 ----- tests/baselines/reference/jsdocReturnTag1.js | 41 +++++ .../reference/jsdocReturnTag1.symbols | 27 ++++ .../baselines/reference/jsdocReturnTag1.types | 32 ++++ tests/baselines/reference/jsdocTypeTag.js | 141 ++++++++++++++++++ .../baselines/reference/jsdocTypeTag.symbols | 138 +++++++++++++++++ tests/baselines/reference/jsdocTypeTag.types | 141 ++++++++++++++++++ tests/baselines/reference/returns.js | 16 -- tests/baselines/reference/returns.symbols | 10 -- tests/baselines/reference/returns.types | 11 -- 26 files changed, 928 insertions(+), 81 deletions(-) create mode 100644 tests/baselines/reference/checkJsdocParamTag1.js create mode 100644 tests/baselines/reference/checkJsdocParamTag1.symbols create mode 100644 tests/baselines/reference/checkJsdocParamTag1.types create mode 100644 tests/baselines/reference/checkJsdocReturnTag1.js create mode 100644 tests/baselines/reference/checkJsdocReturnTag1.symbols create mode 100644 tests/baselines/reference/checkJsdocReturnTag1.types create mode 100644 tests/baselines/reference/checkJsdocReturnTag2.js create mode 100644 tests/baselines/reference/checkJsdocReturnTag2.symbols create mode 100644 tests/baselines/reference/checkJsdocReturnTag2.types rename tests/baselines/reference/{jsDocTypes2.js => checkJsdocTypeTag1.js} (74%) create mode 100644 tests/baselines/reference/checkJsdocTypeTag1.symbols rename tests/baselines/reference/{jsDocTypes2.types => checkJsdocTypeTag1.types} (70%) create mode 100644 tests/baselines/reference/checkJsdocTypeTag2.errors.txt create mode 100644 tests/baselines/reference/checkJsdocTypeTag2.js rename tests/baselines/reference/{jsDocTypes3.errors.txt => checkJsdocTypeTag3.errors.txt} (72%) rename tests/baselines/reference/{jsDocTypes3.js => checkJsdocTypeTag3.js} (100%) delete mode 100644 tests/baselines/reference/jsDocTypes2.symbols create mode 100644 tests/baselines/reference/jsdocReturnTag1.js create mode 100644 tests/baselines/reference/jsdocReturnTag1.symbols create mode 100644 tests/baselines/reference/jsdocReturnTag1.types create mode 100644 tests/baselines/reference/jsdocTypeTag.js create mode 100644 tests/baselines/reference/jsdocTypeTag.symbols create mode 100644 tests/baselines/reference/jsdocTypeTag.types delete mode 100644 tests/baselines/reference/returns.js delete mode 100644 tests/baselines/reference/returns.symbols delete mode 100644 tests/baselines/reference/returns.types diff --git a/tests/baselines/reference/checkJsdocParamTag1.js b/tests/baselines/reference/checkJsdocParamTag1.js new file mode 100644 index 00000000000..577460626a1 --- /dev/null +++ b/tests/baselines/reference/checkJsdocParamTag1.js @@ -0,0 +1,22 @@ +//// [0.js] +// @ts-check +/** + * @param {number=} n + * @param {string} [s] + */ +function foo(n, s) {} + +foo(); +foo(1); +foo(1, "hi"); + +//// [0.js] +// @ts-check +/** + * @param {number=} n + * @param {string} [s] + */ +function foo(n, s) { } +foo(); +foo(1); +foo(1, "hi"); diff --git a/tests/baselines/reference/checkJsdocParamTag1.symbols b/tests/baselines/reference/checkJsdocParamTag1.symbols new file mode 100644 index 00000000000..d16816f908b --- /dev/null +++ b/tests/baselines/reference/checkJsdocParamTag1.symbols @@ -0,0 +1,20 @@ +=== tests/cases/conformance/jsdoc/0.js === +// @ts-check +/** + * @param {number=} n + * @param {string} [s] + */ +function foo(n, s) {} +>foo : Symbol(foo, Decl(0.js, 0, 0)) +>n : Symbol(n, Decl(0.js, 5, 13)) +>s : Symbol(s, Decl(0.js, 5, 15)) + +foo(); +>foo : Symbol(foo, Decl(0.js, 0, 0)) + +foo(1); +>foo : Symbol(foo, Decl(0.js, 0, 0)) + +foo(1, "hi"); +>foo : Symbol(foo, Decl(0.js, 0, 0)) + diff --git a/tests/baselines/reference/checkJsdocParamTag1.types b/tests/baselines/reference/checkJsdocParamTag1.types new file mode 100644 index 00000000000..5b24c3d8887 --- /dev/null +++ b/tests/baselines/reference/checkJsdocParamTag1.types @@ -0,0 +1,26 @@ +=== tests/cases/conformance/jsdoc/0.js === +// @ts-check +/** + * @param {number=} n + * @param {string} [s] + */ +function foo(n, s) {} +>foo : (n?: number, s?: string) => void +>n : number +>s : string + +foo(); +>foo() : void +>foo : (n?: number, s?: string) => void + +foo(1); +>foo(1) : void +>foo : (n?: number, s?: string) => void +>1 : 1 + +foo(1, "hi"); +>foo(1, "hi") : void +>foo : (n?: number, s?: string) => void +>1 : 1 +>"hi" : "hi" + diff --git a/tests/baselines/reference/checkJsdocReturnTag1.js b/tests/baselines/reference/checkJsdocReturnTag1.js new file mode 100644 index 00000000000..31c30e54dfc --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag1.js @@ -0,0 +1,43 @@ +//// [returns.js] +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return "hello"; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return "hello world"; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} + +//// [dummy.js] +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return "hello"; +} +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return "hello world"; +} +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} diff --git a/tests/baselines/reference/checkJsdocReturnTag1.symbols b/tests/baselines/reference/checkJsdocReturnTag1.symbols new file mode 100644 index 00000000000..ec6376d02ab --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag1.symbols @@ -0,0 +1,28 @@ +=== tests/cases/conformance/jsdoc/returns.js === +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : Symbol(f, Decl(returns.js, 0, 0)) + + return "hello"; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { +>f1 : Symbol(f1, Decl(returns.js, 6, 1)) + + return "hello world"; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { +>f2 : Symbol(f2, Decl(returns.js, 13, 1)) + + return 5 || "hello"; +} diff --git a/tests/baselines/reference/checkJsdocReturnTag1.types b/tests/baselines/reference/checkJsdocReturnTag1.types new file mode 100644 index 00000000000..04a2df87c01 --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag1.types @@ -0,0 +1,33 @@ +=== tests/cases/conformance/jsdoc/returns.js === +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : () => string + + return "hello"; +>"hello" : "hello" +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { +>f1 : () => string + + return "hello world"; +>"hello world" : "hello world" +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { +>f2 : () => string | number + + return 5 || "hello"; +>5 || "hello" : "hello" | 5 +>5 : 5 +>"hello" : "hello" +} diff --git a/tests/baselines/reference/checkJsdocReturnTag2.js b/tests/baselines/reference/checkJsdocReturnTag2.js new file mode 100644 index 00000000000..4a68e5d85b7 --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag2.js @@ -0,0 +1,30 @@ +//// [returns.js] +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} + +/** + * @returns {string | number} This comment is not currently exposed + */ +function f1() { + return 5 || true; +} + +//// [dummy.js] +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} +/** + * @returns {string | number} This comment is not currently exposed + */ +function f1() { + return 5 || true; +} diff --git a/tests/baselines/reference/checkJsdocReturnTag2.symbols b/tests/baselines/reference/checkJsdocReturnTag2.symbols new file mode 100644 index 00000000000..43fa1a800e1 --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag2.symbols @@ -0,0 +1,19 @@ +=== tests/cases/conformance/jsdoc/returns.js === +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : Symbol(f, Decl(returns.js, 0, 0)) + + return 5; +} + +/** + * @returns {string | number} This comment is not currently exposed + */ +function f1() { +>f1 : Symbol(f1, Decl(returns.js, 6, 1)) + + return 5 || true; +} diff --git a/tests/baselines/reference/checkJsdocReturnTag2.types b/tests/baselines/reference/checkJsdocReturnTag2.types new file mode 100644 index 00000000000..fe7dca7a364 --- /dev/null +++ b/tests/baselines/reference/checkJsdocReturnTag2.types @@ -0,0 +1,23 @@ +=== tests/cases/conformance/jsdoc/returns.js === +// @ts-check +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : () => string + + return 5; +>5 : 5 +} + +/** + * @returns {string | number} This comment is not currently exposed + */ +function f1() { +>f1 : () => string | number + + return 5 || true; +>5 || true : true | 5 +>5 : 5 +>true : true +} diff --git a/tests/baselines/reference/jsDocTypes2.js b/tests/baselines/reference/checkJsdocTypeTag1.js similarity index 74% rename from tests/baselines/reference/jsDocTypes2.js rename to tests/baselines/reference/checkJsdocTypeTag1.js index a3848704fad..aee738550e3 100644 --- a/tests/baselines/reference/jsDocTypes2.js +++ b/tests/baselines/reference/checkJsdocTypeTag1.js @@ -1,7 +1,14 @@ //// [0.js] // @ts-check +/** @type {String} */ +var S = "hello world"; + +/** @type {number} */ +var n = 10; + /** @type {*} */ var anyT = 2; +anyT = "hello"; /** @type {?} */ var anyT1 = 2; @@ -21,8 +28,13 @@ x2(0); //// [0.js] // @ts-check +/** @type {String} */ +var S = "hello world"; +/** @type {number} */ +var n = 10; /** @type {*} */ var anyT = 2; +anyT = "hello"; /** @type {?} */ var anyT1 = 2; anyT1 = "hi"; diff --git a/tests/baselines/reference/checkJsdocTypeTag1.symbols b/tests/baselines/reference/checkJsdocTypeTag1.symbols new file mode 100644 index 00000000000..39848ff50a8 --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypeTag1.symbols @@ -0,0 +1,51 @@ +=== tests/cases/conformance/jsdoc/0.js === +// @ts-check +/** @type {String} */ +var S = "hello world"; +>S : Symbol(S, Decl(0.js, 2, 3)) + +/** @type {number} */ +var n = 10; +>n : Symbol(n, Decl(0.js, 5, 3)) + +/** @type {*} */ +var anyT = 2; +>anyT : Symbol(anyT, Decl(0.js, 8, 3)) + +anyT = "hello"; +>anyT : Symbol(anyT, Decl(0.js, 8, 3)) + +/** @type {?} */ +var anyT1 = 2; +>anyT1 : Symbol(anyT1, Decl(0.js, 12, 3)) + +anyT1 = "hi"; +>anyT1 : Symbol(anyT1, Decl(0.js, 12, 3)) + +/** @type {Function} */ +const x = (a) => a + 1; +>x : Symbol(x, Decl(0.js, 16, 5)) +>a : Symbol(a, Decl(0.js, 16, 11)) +>a : Symbol(a, Decl(0.js, 16, 11)) + +x(1); +>x : Symbol(x, Decl(0.js, 16, 5)) + +/** @type {function (number)} */ +const x1 = (a) => a + 1; +>x1 : Symbol(x1, Decl(0.js, 20, 5)) +>a : Symbol(a, Decl(0.js, 20, 12)) +>a : Symbol(a, Decl(0.js, 20, 12)) + +x1(0); +>x1 : Symbol(x1, Decl(0.js, 20, 5)) + +/** @type {function (number): number} */ +const x2 = (a) => a + 1; +>x2 : Symbol(x2, Decl(0.js, 24, 5)) +>a : Symbol(a, Decl(0.js, 24, 12)) +>a : Symbol(a, Decl(0.js, 24, 12)) + +x2(0); +>x2 : Symbol(x2, Decl(0.js, 24, 5)) + diff --git a/tests/baselines/reference/jsDocTypes2.types b/tests/baselines/reference/checkJsdocTypeTag1.types similarity index 70% rename from tests/baselines/reference/jsDocTypes2.types rename to tests/baselines/reference/checkJsdocTypeTag1.types index db5a5902d10..4c6597ca147 100644 --- a/tests/baselines/reference/jsDocTypes2.types +++ b/tests/baselines/reference/checkJsdocTypeTag1.types @@ -1,10 +1,25 @@ -=== tests/cases/conformance/salsa/0.js === +=== tests/cases/conformance/jsdoc/0.js === // @ts-check +/** @type {String} */ +var S = "hello world"; +>S : string +>"hello world" : "hello world" + +/** @type {number} */ +var n = 10; +>n : number +>10 : 10 + /** @type {*} */ var anyT = 2; >anyT : any >2 : 2 +anyT = "hello"; +>anyT = "hello" : "hello" +>anyT : any +>"hello" : "hello" + /** @type {?} */ var anyT1 = 2; >anyT1 : any diff --git a/tests/baselines/reference/checkJsdocTypeTag2.errors.txt b/tests/baselines/reference/checkJsdocTypeTag2.errors.txt new file mode 100644 index 00000000000..ca02c578a36 --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypeTag2.errors.txt @@ -0,0 +1,42 @@ +tests/cases/conformance/jsdoc/0.js(3,5): error TS2322: Type 'true' is not assignable to type 'string'. +tests/cases/conformance/jsdoc/0.js(6,5): error TS2322: Type '"hello"' is not assignable to type 'number'. +tests/cases/conformance/jsdoc/0.js(10,4): error TS2345: Argument of type '"string"' is not assignable to parameter of type 'number'. +tests/cases/conformance/jsdoc/0.js(13,7): error TS2451: Cannot redeclare block-scoped variable 'x2'. +tests/cases/conformance/jsdoc/0.js(17,1): error TS2322: Type 'number' is not assignable to type 'string'. +tests/cases/conformance/jsdoc/0.js(20,7): error TS2451: Cannot redeclare block-scoped variable 'x2'. + + +==== tests/cases/conformance/jsdoc/0.js (6 errors) ==== + // @ts-check + /** @type {String} */ + var S = true; + ~ +!!! error TS2322: Type 'true' is not assignable to type 'string'. + + /** @type {number} */ + var n = "hello"; + ~ +!!! error TS2322: Type '"hello"' is not assignable to type 'number'. + + /** @type {function (number)} */ + const x1 = (a) => a + 1; + x1("string"); + ~~~~~~~~ +!!! error TS2345: Argument of type '"string"' is not assignable to parameter of type 'number'. + + /** @type {function (number): number} */ + const x2 = (a) => a + 1; + ~~ +!!! error TS2451: Cannot redeclare block-scoped variable 'x2'. + + /** @type {string} */ + var a; + a = x2(0); + ~ +!!! error TS2322: Type 'number' is not assignable to type 'string'. + + /** @type {function (number): number} */ + const x2 = (a) => a.concat("hi"); + ~~ +!!! error TS2451: Cannot redeclare block-scoped variable 'x2'. + x2(0); \ No newline at end of file diff --git a/tests/baselines/reference/checkJsdocTypeTag2.js b/tests/baselines/reference/checkJsdocTypeTag2.js new file mode 100644 index 00000000000..23b436e2031 --- /dev/null +++ b/tests/baselines/reference/checkJsdocTypeTag2.js @@ -0,0 +1,40 @@ +//// [0.js] +// @ts-check +/** @type {String} */ +var S = true; + +/** @type {number} */ +var n = "hello"; + +/** @type {function (number)} */ +const x1 = (a) => a + 1; +x1("string"); + +/** @type {function (number): number} */ +const x2 = (a) => a + 1; + +/** @type {string} */ +var a; +a = x2(0); + +/** @type {function (number): number} */ +const x2 = (a) => a.concat("hi"); +x2(0); + +//// [0.js] +// @ts-check +/** @type {String} */ +var S = true; +/** @type {number} */ +var n = "hello"; +/** @type {function (number)} */ +var x1 = function (a) { return a + 1; }; +x1("string"); +/** @type {function (number): number} */ +var x2 = function (a) { return a + 1; }; +/** @type {string} */ +var a; +a = x2(0); +/** @type {function (number): number} */ +var x2 = function (a) { return a.concat("hi"); }; +x2(0); diff --git a/tests/baselines/reference/jsDocTypes3.errors.txt b/tests/baselines/reference/checkJsdocTypeTag3.errors.txt similarity index 72% rename from tests/baselines/reference/jsDocTypes3.errors.txt rename to tests/baselines/reference/checkJsdocTypeTag3.errors.txt index 5f5feeaf0a7..d53c0972fa3 100644 --- a/tests/baselines/reference/jsDocTypes3.errors.txt +++ b/tests/baselines/reference/checkJsdocTypeTag3.errors.txt @@ -1,8 +1,8 @@ -tests/cases/conformance/salsa/0.js(5,4): error TS2345: Argument of type '"string"' is not assignable to parameter of type 'number'. -tests/cases/conformance/salsa/0.js(12,1): error TS2322: Type 'number' is not assignable to type 'string'. +tests/cases/conformance/jsdoc/0.js(5,4): error TS2345: Argument of type '"string"' is not assignable to parameter of type 'number'. +tests/cases/conformance/jsdoc/0.js(12,1): error TS2322: Type 'number' is not assignable to type 'string'. -==== tests/cases/conformance/salsa/0.js (2 errors) ==== +==== tests/cases/conformance/jsdoc/0.js (2 errors) ==== // @ts-check /** @type {function (number)} */ diff --git a/tests/baselines/reference/jsDocTypes3.js b/tests/baselines/reference/checkJsdocTypeTag3.js similarity index 100% rename from tests/baselines/reference/jsDocTypes3.js rename to tests/baselines/reference/checkJsdocTypeTag3.js diff --git a/tests/baselines/reference/jsDocTypes2.symbols b/tests/baselines/reference/jsDocTypes2.symbols deleted file mode 100644 index 96b32b9ad91..00000000000 --- a/tests/baselines/reference/jsDocTypes2.symbols +++ /dev/null @@ -1,40 +0,0 @@ -=== tests/cases/conformance/salsa/0.js === -// @ts-check -/** @type {*} */ -var anyT = 2; ->anyT : Symbol(anyT, Decl(0.js, 2, 3)) - -/** @type {?} */ -var anyT1 = 2; ->anyT1 : Symbol(anyT1, Decl(0.js, 5, 3)) - -anyT1 = "hi"; ->anyT1 : Symbol(anyT1, Decl(0.js, 5, 3)) - -/** @type {Function} */ -const x = (a) => a + 1; ->x : Symbol(x, Decl(0.js, 9, 5)) ->a : Symbol(a, Decl(0.js, 9, 11)) ->a : Symbol(a, Decl(0.js, 9, 11)) - -x(1); ->x : Symbol(x, Decl(0.js, 9, 5)) - -/** @type {function (number)} */ -const x1 = (a) => a + 1; ->x1 : Symbol(x1, Decl(0.js, 13, 5)) ->a : Symbol(a, Decl(0.js, 13, 12)) ->a : Symbol(a, Decl(0.js, 13, 12)) - -x1(0); ->x1 : Symbol(x1, Decl(0.js, 13, 5)) - -/** @type {function (number): number} */ -const x2 = (a) => a + 1; ->x2 : Symbol(x2, Decl(0.js, 17, 5)) ->a : Symbol(a, Decl(0.js, 17, 12)) ->a : Symbol(a, Decl(0.js, 17, 12)) - -x2(0); ->x2 : Symbol(x2, Decl(0.js, 17, 5)) - diff --git a/tests/baselines/reference/jsdocReturnTag1.js b/tests/baselines/reference/jsdocReturnTag1.js new file mode 100644 index 00000000000..5cb0dfedf87 --- /dev/null +++ b/tests/baselines/reference/jsdocReturnTag1.js @@ -0,0 +1,41 @@ +//// [returns.js] +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return 5; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} + +//// [dummy.js] +/** + * @returns {string} This comment is not currently exposed + */ +function f() { + return 5; +} +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { + return 5; +} +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { + return 5 || "hello"; +} diff --git a/tests/baselines/reference/jsdocReturnTag1.symbols b/tests/baselines/reference/jsdocReturnTag1.symbols new file mode 100644 index 00000000000..5dd83a0b8eb --- /dev/null +++ b/tests/baselines/reference/jsdocReturnTag1.symbols @@ -0,0 +1,27 @@ +=== tests/cases/conformance/jsdoc/returns.js === +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : Symbol(f, Decl(returns.js, 0, 0)) + + return 5; +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { +>f1 : Symbol(f1, Decl(returns.js, 5, 1)) + + return 5; +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { +>f2 : Symbol(f2, Decl(returns.js, 12, 1)) + + return 5 || "hello"; +} diff --git a/tests/baselines/reference/jsdocReturnTag1.types b/tests/baselines/reference/jsdocReturnTag1.types new file mode 100644 index 00000000000..d2a5891b29a --- /dev/null +++ b/tests/baselines/reference/jsdocReturnTag1.types @@ -0,0 +1,32 @@ +=== tests/cases/conformance/jsdoc/returns.js === +/** + * @returns {string} This comment is not currently exposed + */ +function f() { +>f : () => string + + return 5; +>5 : 5 +} + +/** + * @returns {string=} This comment is not currently exposed + */ +function f1() { +>f1 : () => string + + return 5; +>5 : 5 +} + +/** + * @returns {string|number} This comment is not currently exposed + */ +function f2() { +>f2 : () => string | number + + return 5 || "hello"; +>5 || "hello" : 5 | "hello" +>5 : 5 +>"hello" : "hello" +} diff --git a/tests/baselines/reference/jsdocTypeTag.js b/tests/baselines/reference/jsdocTypeTag.js new file mode 100644 index 00000000000..ff92f0f0474 --- /dev/null +++ b/tests/baselines/reference/jsdocTypeTag.js @@ -0,0 +1,141 @@ +//// [tests/cases/conformance/jsdoc/jsdocTypeTag.ts] //// + +//// [a.js] +/** @type {String} */ +var S; + +/** @type {string} */ +var s; + +/** @type {Number} */ +var N; + +/** @type {number} */ +var n; + +/** @type {Boolean} */ +var B; + +/** @type {boolean} */ +var b; + +/** @type {Void} */ +var V; + +/** @type {void} */ +var v; + +/** @type {Undefined} */ +var U; + +/** @type {undefined} */ +var u; + +/** @type {Null} */ +var Nl; + +/** @type {null} */ +var nl; + +/** @type {Array} */ +var A; + +/** @type {array} */ +var a; + +/** @type {Promise} */ +var P; + +/** @type {promise} */ +var p; + +/** @type {?number} */ +var nullable; + +/** @type {Object} */ +var Obj; + +/** @type {Function} */ +var Func; + +//// [b.ts] +var S: string; +var s: string; +var N: number; +var n: number +var B: boolean; +var b: boolean; +var V :void; +var v: void; +var U: undefined; +var u: undefined; +var Nl: null; +var nl: null; +var A: any[]; +var a: any[]; +var P: Promise; +var p: Promise; +var nullable: number | null; +var Obj: any; +var Func: Function; + + +//// [a.js] +/** @type {String} */ +var S; +/** @type {string} */ +var s; +/** @type {Number} */ +var N; +/** @type {number} */ +var n; +/** @type {Boolean} */ +var B; +/** @type {boolean} */ +var b; +/** @type {Void} */ +var V; +/** @type {void} */ +var v; +/** @type {Undefined} */ +var U; +/** @type {undefined} */ +var u; +/** @type {Null} */ +var Nl; +/** @type {null} */ +var nl; +/** @type {Array} */ +var A; +/** @type {array} */ +var a; +/** @type {Promise} */ +var P; +/** @type {promise} */ +var p; +/** @type {?number} */ +var nullable; +/** @type {Object} */ +var Obj; +/** @type {Function} */ +var Func; +//// [b.js] +var S; +var s; +var N; +var n; +var B; +var b; +var V; +var v; +var U; +var u; +var Nl; +var nl; +var A; +var a; +var P; +var p; +var nullable; +var Obj; +var Func; diff --git a/tests/baselines/reference/jsdocTypeTag.symbols b/tests/baselines/reference/jsdocTypeTag.symbols new file mode 100644 index 00000000000..5931c1cfe53 --- /dev/null +++ b/tests/baselines/reference/jsdocTypeTag.symbols @@ -0,0 +1,138 @@ +=== tests/cases/conformance/jsdoc/a.js === +/** @type {String} */ +var S; +>S : Symbol(S, Decl(a.js, 1, 3), Decl(b.ts, 0, 3)) + +/** @type {string} */ +var s; +>s : Symbol(s, Decl(a.js, 4, 3), Decl(b.ts, 1, 3)) + +/** @type {Number} */ +var N; +>N : Symbol(N, Decl(a.js, 7, 3), Decl(b.ts, 2, 3)) + +/** @type {number} */ +var n; +>n : Symbol(n, Decl(a.js, 10, 3), Decl(b.ts, 3, 3)) + +/** @type {Boolean} */ +var B; +>B : Symbol(B, Decl(a.js, 13, 3), Decl(b.ts, 4, 3)) + +/** @type {boolean} */ +var b; +>b : Symbol(b, Decl(a.js, 16, 3), Decl(b.ts, 5, 3)) + +/** @type {Void} */ +var V; +>V : Symbol(V, Decl(a.js, 19, 3), Decl(b.ts, 6, 3)) + +/** @type {void} */ +var v; +>v : Symbol(v, Decl(a.js, 22, 3), Decl(b.ts, 7, 3)) + +/** @type {Undefined} */ +var U; +>U : Symbol(U, Decl(a.js, 25, 3), Decl(b.ts, 8, 3)) + +/** @type {undefined} */ +var u; +>u : Symbol(u, Decl(a.js, 28, 3), Decl(b.ts, 9, 3)) + +/** @type {Null} */ +var Nl; +>Nl : Symbol(Nl, Decl(a.js, 31, 3), Decl(b.ts, 10, 3)) + +/** @type {null} */ +var nl; +>nl : Symbol(nl, Decl(a.js, 34, 3), Decl(b.ts, 11, 3)) + +/** @type {Array} */ +var A; +>A : Symbol(A, Decl(a.js, 37, 3), Decl(b.ts, 12, 3)) + +/** @type {array} */ +var a; +>a : Symbol(a, Decl(a.js, 40, 3), Decl(b.ts, 13, 3)) + +/** @type {Promise} */ +var P; +>P : Symbol(P, Decl(a.js, 43, 3), Decl(b.ts, 14, 3)) + +/** @type {promise} */ +var p; +>p : Symbol(p, Decl(a.js, 46, 3), Decl(b.ts, 15, 3)) + +/** @type {?number} */ +var nullable; +>nullable : Symbol(nullable, Decl(a.js, 49, 3), Decl(b.ts, 16, 3)) + +/** @type {Object} */ +var Obj; +>Obj : Symbol(Obj, Decl(a.js, 52, 3), Decl(b.ts, 17, 3)) + +/** @type {Function} */ +var Func; +>Func : Symbol(Func, Decl(a.js, 55, 3), Decl(b.ts, 18, 3)) + +=== tests/cases/conformance/jsdoc/b.ts === +var S: string; +>S : Symbol(S, Decl(a.js, 1, 3), Decl(b.ts, 0, 3)) + +var s: string; +>s : Symbol(s, Decl(a.js, 4, 3), Decl(b.ts, 1, 3)) + +var N: number; +>N : Symbol(N, Decl(a.js, 7, 3), Decl(b.ts, 2, 3)) + +var n: number +>n : Symbol(n, Decl(a.js, 10, 3), Decl(b.ts, 3, 3)) + +var B: boolean; +>B : Symbol(B, Decl(a.js, 13, 3), Decl(b.ts, 4, 3)) + +var b: boolean; +>b : Symbol(b, Decl(a.js, 16, 3), Decl(b.ts, 5, 3)) + +var V :void; +>V : Symbol(V, Decl(a.js, 19, 3), Decl(b.ts, 6, 3)) + +var v: void; +>v : Symbol(v, Decl(a.js, 22, 3), Decl(b.ts, 7, 3)) + +var U: undefined; +>U : Symbol(U, Decl(a.js, 25, 3), Decl(b.ts, 8, 3)) + +var u: undefined; +>u : Symbol(u, Decl(a.js, 28, 3), Decl(b.ts, 9, 3)) + +var Nl: null; +>Nl : Symbol(Nl, Decl(a.js, 31, 3), Decl(b.ts, 10, 3)) + +var nl: null; +>nl : Symbol(nl, Decl(a.js, 34, 3), Decl(b.ts, 11, 3)) + +var A: any[]; +>A : Symbol(A, Decl(a.js, 37, 3), Decl(b.ts, 12, 3)) + +var a: any[]; +>a : Symbol(a, Decl(a.js, 40, 3), Decl(b.ts, 13, 3)) + +var P: Promise; +>P : Symbol(P, Decl(a.js, 43, 3), Decl(b.ts, 14, 3)) +>Promise : Symbol(Promise, Decl(lib.d.ts, --, --)) + +var p: Promise; +>p : Symbol(p, Decl(a.js, 46, 3), Decl(b.ts, 15, 3)) +>Promise : Symbol(Promise, Decl(lib.d.ts, --, --)) + +var nullable: number | null; +>nullable : Symbol(nullable, Decl(a.js, 49, 3), Decl(b.ts, 16, 3)) + +var Obj: any; +>Obj : Symbol(Obj, Decl(a.js, 52, 3), Decl(b.ts, 17, 3)) + +var Func: Function; +>Func : Symbol(Func, Decl(a.js, 55, 3), Decl(b.ts, 18, 3)) +>Function : Symbol(Function, Decl(lib.d.ts, --, --), Decl(lib.d.ts, --, --)) + diff --git a/tests/baselines/reference/jsdocTypeTag.types b/tests/baselines/reference/jsdocTypeTag.types new file mode 100644 index 00000000000..f3e7dfad634 --- /dev/null +++ b/tests/baselines/reference/jsdocTypeTag.types @@ -0,0 +1,141 @@ +=== tests/cases/conformance/jsdoc/a.js === +/** @type {String} */ +var S; +>S : string + +/** @type {string} */ +var s; +>s : string + +/** @type {Number} */ +var N; +>N : number + +/** @type {number} */ +var n; +>n : number + +/** @type {Boolean} */ +var B; +>B : boolean + +/** @type {boolean} */ +var b; +>b : boolean + +/** @type {Void} */ +var V; +>V : void + +/** @type {void} */ +var v; +>v : void + +/** @type {Undefined} */ +var U; +>U : undefined + +/** @type {undefined} */ +var u; +>u : undefined + +/** @type {Null} */ +var Nl; +>Nl : null + +/** @type {null} */ +var nl; +>nl : null + +/** @type {Array} */ +var A; +>A : any[] + +/** @type {array} */ +var a; +>a : any[] + +/** @type {Promise} */ +var P; +>P : Promise + +/** @type {promise} */ +var p; +>p : Promise + +/** @type {?number} */ +var nullable; +>nullable : number | null + +/** @type {Object} */ +var Obj; +>Obj : any + +/** @type {Function} */ +var Func; +>Func : Function + +=== tests/cases/conformance/jsdoc/b.ts === +var S: string; +>S : string + +var s: string; +>s : string + +var N: number; +>N : number + +var n: number +>n : number + +var B: boolean; +>B : boolean + +var b: boolean; +>b : boolean + +var V :void; +>V : void + +var v: void; +>v : void + +var U: undefined; +>U : undefined + +var u: undefined; +>u : undefined + +var Nl: null; +>Nl : null +>null : null + +var nl: null; +>nl : null +>null : null + +var A: any[]; +>A : any[] + +var a: any[]; +>a : any[] + +var P: Promise; +>P : Promise +>Promise : Promise + +var p: Promise; +>p : Promise +>Promise : Promise + +var nullable: number | null; +>nullable : number | null +>null : null + +var Obj: any; +>Obj : any + +var Func: Function; +>Func : Function +>Function : Function + diff --git a/tests/baselines/reference/returns.js b/tests/baselines/reference/returns.js deleted file mode 100644 index 67390dea72a..00000000000 --- a/tests/baselines/reference/returns.js +++ /dev/null @@ -1,16 +0,0 @@ -//// [returns.js] -/** - * @returns {string} This comment is not currently exposed - */ -function f() { - return ""; -} - - -//// [dummy.js] -/** - * @returns {string} This comment is not currently exposed - */ -function f() { - return ""; -} diff --git a/tests/baselines/reference/returns.symbols b/tests/baselines/reference/returns.symbols deleted file mode 100644 index e0f0d4dac96..00000000000 --- a/tests/baselines/reference/returns.symbols +++ /dev/null @@ -1,10 +0,0 @@ -=== tests/cases/conformance/jsdoc/returns.js === -/** - * @returns {string} This comment is not currently exposed - */ -function f() { ->f : Symbol(f, Decl(returns.js, 0, 0)) - - return ""; -} - diff --git a/tests/baselines/reference/returns.types b/tests/baselines/reference/returns.types deleted file mode 100644 index c85bc7272f8..00000000000 --- a/tests/baselines/reference/returns.types +++ /dev/null @@ -1,11 +0,0 @@ -=== tests/cases/conformance/jsdoc/returns.js === -/** - * @returns {string} This comment is not currently exposed - */ -function f() { ->f : () => string - - return ""; ->"" : "" -} - From 9c102461d96fb7293b03e99d89aaa55e742c4101 Mon Sep 17 00:00:00 2001 From: Yui T Date: Fri, 26 May 2017 19:08:08 -0700 Subject: [PATCH 31/56] Rename parameterName to name --- src/compiler/parser.ts | 2 +- src/compiler/types.ts | 2 +- src/compiler/utilities.ts | 4 ++-- .../DocComments.parsesCorrectly.argSynonymForParamTag.json | 2 +- ...ocComments.parsesCorrectly.argumentSynonymForParamTag.json | 2 +- .../JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json | 2 +- .../JSDocParsing/DocComments.parsesCorrectly.paramTag1.json | 2 +- .../DocComments.parsesCorrectly.paramTagBracketedName1.json | 2 +- .../DocComments.parsesCorrectly.paramTagBracketedName2.json | 2 +- .../DocComments.parsesCorrectly.paramTagNameThenType1.json | 2 +- .../DocComments.parsesCorrectly.paramTagNameThenType2.json | 2 +- .../DocComments.parsesCorrectly.paramWithoutType.json | 2 +- .../DocComments.parsesCorrectly.twoParamTag2.json | 4 ++-- .../DocComments.parsesCorrectly.twoParamTagOnSameLine.json | 4 ++-- 14 files changed, 17 insertions(+), 17 deletions(-) diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 07d4a9ada41..cd9cd7c247d 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6682,7 +6682,7 @@ namespace ts { result.preParameterName = preName; result.typeExpression = typeExpression; result.postParameterName = postName; - result.parameterName = postName || preName; + result.name = postName || preName; result.isBracketed = isBracketed; return finishNode(result); } diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 6f602ff23af..d8d6c174c12 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -2163,7 +2163,7 @@ namespace ts { /** the parameter name, if provided *after* the type (JSDoc-standard) */ postParameterName?: Identifier; /** the parameter name, regardless of the location it was provided */ - parameterName: Identifier; + name: Identifier; isBracketed: boolean; } diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 134404c247b..506d2728ffd 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -1635,7 +1635,7 @@ namespace ts { } else if (param.name.kind === SyntaxKind.Identifier) { const name = (param.name as Identifier).text; - return filter(tags, tag => tag.kind === SyntaxKind.JSDocParameterTag && tag.parameterName.text === name); + return filter(tags, tag => tag.kind === SyntaxKind.JSDocParameterTag && tag.name.text === name); } else { // TODO: it's a destructured parameter, so it should look up an "object type" series of multiple lines @@ -1646,7 +1646,7 @@ namespace ts { /** Does the opposite of `getJSDocParameterTags`: given a JSDoc parameter, finds the parameter corresponding to it. */ export function getParameterFromJSDoc(node: JSDocParameterTag): ParameterDeclaration | undefined { - const name = node.parameterName.text; + const name = node.name.text; const grandParent = node.parent!.parent!; Debug.assert(node.parent!.kind === SyntaxKind.JSDocComment); if (!isFunctionLike(grandParent)) { diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json index 064a040c58f..7e4346eba68 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json @@ -34,7 +34,7 @@ "end": 27, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 22, "end": 27, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json index 264b5850223..e46a09e6561 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json @@ -34,7 +34,7 @@ "end": 32, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 27, "end": 32, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json index 9d303955ab1..af20bf8d6bb 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json @@ -34,7 +34,7 @@ "end": 29, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 24, "end": 29, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json index 1b87d268b93..5e0c3d21744 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json @@ -34,7 +34,7 @@ "end": 29, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 24, "end": 29, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName1.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName1.json index fe01df58851..1df54fadcd7 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName1.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName1.json @@ -34,7 +34,7 @@ "end": 30, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 25, "end": 30, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName2.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName2.json index f50ce732606..5347b99be7a 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName2.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagBracketedName2.json @@ -34,7 +34,7 @@ "end": 31, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 26, "end": 31, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType1.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType1.json index 70f2641fd51..204d94779b3 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType1.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType1.json @@ -34,7 +34,7 @@ "end": 28 } }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 15, "end": 20, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType2.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType2.json index 4b720567cc7..7c79459768b 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType2.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTagNameThenType2.json @@ -34,7 +34,7 @@ "end": 28 } }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 15, "end": 20, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json index d77e80c7512..17036e3729a 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json @@ -24,7 +24,7 @@ "end": 18, "text": "foo" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 15, "end": 18, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json index 16968061afc..d5d04dce69c 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json @@ -34,7 +34,7 @@ "end": 29, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 24, "end": 29, @@ -73,7 +73,7 @@ "end": 55, "text": "name2" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 50, "end": 55, diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json index 8818c3a909e..4c85b2c9aed 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json @@ -34,7 +34,7 @@ "end": 29, "text": "name1" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 24, "end": 29, @@ -73,7 +73,7 @@ "end": 51, "text": "name2" }, - "parameterName": { + "name": { "kind": "Identifier", "pos": 46, "end": 51, From b8ee1691af02f3cddad487f55def6df27b0cad66 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Sat, 27 May 2017 13:07:27 -0700 Subject: [PATCH 32/56] Add wrapper to emit statics/decorators inside es5 class --- src/compiler/core.ts | 72 +- src/compiler/factory.ts | 90 +- src/compiler/sys.ts | 5 + src/compiler/transformers/es2015.ts | 151 ++- src/compiler/transformers/ts.ts | 121 ++- src/compiler/types.ts | 45 +- src/compiler/utilities.ts | 209 +++- src/compiler/visitor.ts | 93 +- ...ticVariableAndExportedVarThatShareAName.js | 4 +- ...VariableAndNonExportedVarThatShareAName.js | 4 +- ...onWithInvalidConstOnPropertyDeclaration.js | 2 +- .../amdImportNotAsPrimaryExpression.js | 2 +- tests/baselines/reference/autolift4.js | 2 +- .../blockScopedNamespaceDifferentFile.js | 4 +- .../blockScopedVariablesUseBeforeDef.js | 2 +- tests/baselines/reference/class2.js | 2 +- .../baselines/reference/classBlockScoping.js | 2 +- .../classExpressionWithDecorator1.js | 8 +- .../classMemberInitializerScoping.js | 2 +- .../classMemberInitializerWithLamdaScoping.js | 14 +- .../reference/classWithPrivateProperty.js | 2 +- .../reference/classWithProtectedProperty.js | 2 +- .../reference/classWithPublicProperty.js | 2 +- .../reference/cloduleStaticMembers.js | 4 +- .../commentOnDecoratedClassDeclaration.js | 12 +- .../reference/commentsOnStaticMembers.js | 16 +- .../commonJSImportAsPrimaryExpression.js | 2 +- .../commonJSImportNotAsPrimaryExpression.js | 2 +- .../reference/computedPropertyNames12_ES5.js | 2 +- .../constructableDecoratorOnClass01.js | 6 +- .../reference/declFilePrivateStatic.js | 4 +- .../reference/decoratorCallGeneric.js | 6 +- .../decoratorChecksFunctionBodies.js | 14 +- ...ratorInstantiateModulesInFunctionBodies.js | 6 +- .../baselines/reference/decoratorMetadata.js | 20 +- ...taForMethodWithNoReturnTypeAnnotation01.js | 12 +- .../decoratorMetadataOnInferredType.js | 8 +- ...orMetadataRestParameterWithImportedType.js | 20 +- .../decoratorMetadataWithConstructorType.js | 8 +- ...adataWithImportDeclarationNameCollision.js | 8 +- ...dataWithImportDeclarationNameCollision2.js | 8 +- ...dataWithImportDeclarationNameCollision3.js | 8 +- ...dataWithImportDeclarationNameCollision4.js | 10 +- ...dataWithImportDeclarationNameCollision5.js | 8 +- ...dataWithImportDeclarationNameCollision6.js | 8 +- ...dataWithImportDeclarationNameCollision7.js | 8 +- ...dataWithImportDeclarationNameCollision8.js | 8 +- .../baselines/reference/decoratorOnClass1.js | 6 +- .../baselines/reference/decoratorOnClass2.js | 6 +- .../baselines/reference/decoratorOnClass3.js | 6 +- .../baselines/reference/decoratorOnClass4.js | 6 +- .../baselines/reference/decoratorOnClass5.js | 6 +- .../baselines/reference/decoratorOnClass8.js | 6 +- .../reference/decoratorOnClassAccessor1.js | 6 +- .../reference/decoratorOnClassAccessor2.js | 6 +- .../reference/decoratorOnClassAccessor3.js | 6 +- .../reference/decoratorOnClassAccessor4.js | 6 +- .../reference/decoratorOnClassAccessor5.js | 6 +- .../reference/decoratorOnClassAccessor6.js | 6 +- .../reference/decoratorOnClassAccessor7.js | 36 +- .../reference/decoratorOnClassAccessor8.js | 60 +- .../reference/decoratorOnClassConstructor2.js | 6 +- .../reference/decoratorOnClassConstructor3.js | 6 +- .../reference/decoratorOnClassConstructor4.js | 20 +- .../decoratorOnClassConstructorParameter1.js | 6 +- .../decoratorOnClassConstructorParameter4.js | 6 +- .../reference/decoratorOnClassMethod1.js | 6 +- .../reference/decoratorOnClassMethod10.js | 6 +- .../reference/decoratorOnClassMethod11.js | 6 +- .../reference/decoratorOnClassMethod12.js | 6 +- .../reference/decoratorOnClassMethod2.js | 6 +- .../reference/decoratorOnClassMethod3.js | 6 +- .../reference/decoratorOnClassMethod8.js | 6 +- .../decoratorOnClassMethodOverload2.js | 6 +- .../decoratorOnClassMethodParameter1.js | 6 +- .../reference/decoratorOnClassProperty1.js | 6 +- .../reference/decoratorOnClassProperty10.js | 6 +- .../reference/decoratorOnClassProperty11.js | 6 +- .../reference/decoratorOnClassProperty2.js | 6 +- .../reference/decoratorOnClassProperty3.js | 6 +- .../reference/decoratorOnClassProperty6.js | 6 +- .../reference/decoratorOnClassProperty7.js | 6 +- .../decoratorWithUnderscoreMethod.js | 6 +- ...dClassSuperCallsInNonConstructorMembers.js | 2 +- .../reference/emitDecoratorMetadata_object.js | 20 +- .../emitDecoratorMetadata_restArgs.js | 40 +- tests/baselines/reference/errorSuperCalls.js | 4 +- .../reference/errorSuperPropertyAccess.js | 4 +- .../reference/es3defaultAliasIsQuoted.js | 2 +- tests/baselines/reference/es6ClassTest.js | 2 +- tests/baselines/reference/es6ClassTest2.js | 2 +- .../reference/es6modulekindWithES5Target.js | 10 +- .../reference/es6modulekindWithES5Target11.js | 16 +- .../reference/es6modulekindWithES5Target2.js | 2 +- .../reference/es6modulekindWithES5Target3.js | 8 +- tests/baselines/reference/extendFromAny.js | 2 +- .../reference/forwardRefInClassProperties.js | 4 +- .../reference/generatedContextualTyping.js | 72 +- ...nericClassWithStaticsUsingTypeArguments.js | 8 +- .../baselines/reference/gettersAndSetters.js | 2 +- tests/baselines/reference/importHelpers.js | 36 +- .../importHelpersInIsolatedModules.js | 36 +- .../reference/importHelpersNoHelpers.js | 36 +- .../reference/importHelpersNoModule.js | 36 +- .../reference/importImportOnlyModule.js | 2 +- .../inferringClassMembersFromAssignments.js | 17 +- .../instanceAndStaticDeclarations1.js | 2 +- .../reference/invalidNewTarget.es5.js | 2 +- .../baselines/reference/invalidStaticField.js | 2 +- .../reference/metadataOfClassFromAlias.js | 8 +- .../reference/metadataOfClassFromAlias2.js | 8 +- .../reference/metadataOfClassFromModule.js | 8 +- .../reference/metadataOfEventAlias.js | 8 +- .../reference/metadataOfStringLiteral.js | 8 +- tests/baselines/reference/metadataOfUnion.js | 56 +- .../reference/metadataOfUnionWithNull.js | 96 +- .../reference/missingDecoratorType.js | 6 +- tests/baselines/reference/newTarget.es5.js | 8 +- tests/baselines/reference/noEmitHelpers2.js | 10 +- .../parserAccessibilityAfterStatic3.js | 2 +- ...ErrorRecovery_IncompleteMemberVariable1.js | 4 +- ...ErrorRecovery_IncompleteMemberVariable2.js | 4 +- tests/baselines/reference/parserharness.js | 6 +- .../privacyCannotNameVarTypeDeclFile.js | 24 +- .../privateStaticMemberAccessibility.js | 2 +- .../amd/main.js | 10 +- .../node/main.js | 10 +- .../amd/main.js | 10 +- .../node/main.js | 10 +- .../emitDecoratorMetadataSystemJS/amd/main.js | 10 +- .../node/main.js | 10 +- .../amd/main.js | 10 +- .../node/main.js | 10 +- .../amd/main.js | 10 +- .../node/main.js | 10 +- .../reference/propertyAccessibility2.js | 2 +- .../reference/quotedPropertyName2.js | 2 +- .../baselines/reference/reassignStaticProp.js | 2 +- .../reference/scopeCheckStaticInitializer.js | 12 +- .../reference/sourceMap-FileWithComments.js | 4 +- .../sourceMap-FileWithComments.js.map | 2 +- .../sourceMap-FileWithComments.sourcemap.txt | 139 +-- .../sourceMapValidationDecorators.js | 62 +- .../sourceMapValidationDecorators.js.map | 2 +- ...ourceMapValidationDecorators.sourcemap.txt | 985 +++++++++--------- ...nonymousTypeNotReferencingTypeParameter.js | 2 +- tests/baselines/reference/staticClassProps.js | 2 +- .../staticMemberAccessOffDerivedType1.js | 2 +- .../reference/staticMemberInitialization.js | 2 +- .../staticMemberWithStringAndNumberNames.js | 10 +- .../reference/staticModifierAlreadySeen.js | 2 +- tests/baselines/reference/staticPropSuper.js | 2 +- tests/baselines/reference/statics.js | 6 +- .../reference/staticsInConstructorBodies.js | 2 +- .../reference/staticsNotInScopeInClodule.js | 2 +- .../reference/strictModeInConstructor.js | 6 +- tests/baselines/reference/superAccess.js | 2 +- tests/baselines/reference/superAccess2.js | 2 +- ...thisInArrowFunctionInStaticInitializer1.js | 9 +- .../reference/thisInConstructorParameter2.js | 2 +- .../reference/thisInInvalidContexts.js | 2 +- .../thisInInvalidContextsExternalModule.js | 2 +- .../reference/thisInOuterClassBody.js | 2 +- .../thisInPropertyBoundDeclarations.js | 10 +- .../reference/thisInStaticMethod1.js | 2 +- tests/baselines/reference/thisTypeErrors.js | 2 +- ...ata when transpile with CommonJS option.js | 10 +- ...adata when transpile with System option.js | 11 +- ... with emit decorators and emit metadata.js | 10 +- .../baselines/reference/tsxDefaultImports.js | 2 +- tests/baselines/reference/typeOfPrototype.js | 2 +- .../reference/typeOfThisInStaticMembers2.js | 4 +- tests/baselines/reference/typeQueryOnClass.js | 4 +- .../reference/typeofUsedBeforeBlockScoped.js | 2 +- .../unqualifiedCallToClassStatic1.js | 8 +- tests/baselines/reference/witness.js | 2 +- 176 files changed, 1955 insertions(+), 1474 deletions(-) diff --git a/src/compiler/core.ts b/src/compiler/core.ts index 60553fdab01..fec9b9092c2 100644 --- a/src/compiler/core.ts +++ b/src/compiler/core.ts @@ -776,28 +776,34 @@ namespace ts { return true; } + /** + * Returns the element at a specific offset in an array if non-empty, `undefined` otherwise. + * A negative offset indicates the element should be retrieved from the end of the array. + */ + export function elementAt(array: T[] | undefined, offset: number): T | undefined { + return array && array.length > 0 && (offset < 0 ? ~offset : offset) < array.length + ? array[offset < 0 ? array.length + offset : offset] + : undefined; + } + /** * Returns the first element of an array if non-empty, `undefined` otherwise. */ - export function firstOrUndefined(array: T[]): T { - return array && array.length > 0 - ? array[0] - : undefined; + export function firstOrUndefined(array: T[]): T | undefined { + return elementAt(array, 0); } /** * Returns the last element of an array if non-empty, `undefined` otherwise. */ - export function lastOrUndefined(array: T[]): T { - return array && array.length > 0 - ? array[array.length - 1] - : undefined; + export function lastOrUndefined(array: T[]): T | undefined { + return elementAt(array, -1); } /** * Returns the only element of an array if it contains only one element, `undefined` otherwise. */ - export function singleOrUndefined(array: T[]): T { + export function singleOrUndefined(array: T[]): T | undefined { return array && array.length === 1 ? array[0] : undefined; @@ -1125,6 +1131,15 @@ namespace ts { return Array.isArray ? Array.isArray(value) : value instanceof Array; } + export function tryCast(value: TIn | undefined, test: (value: TIn) => value is TOut): TOut | undefined { + return value !== undefined && test(value) ? value : undefined; + } + + export function cast(value: TIn | undefined, test: (value: TIn) => value is TOut): TOut { + if (value !== undefined && test(value)) return value; + Debug.fail(`Invalid cast. The supplied value did not pass the test '${Debug.getFunctionName(test)}'.`); + } + /** Does nothing. */ export function noop(): void {} @@ -2204,8 +2219,11 @@ namespace ts { this.declarations = undefined; } - function Type(this: Type, _checker: TypeChecker, flags: TypeFlags) { + function Type(this: Type, checker: TypeChecker, flags: TypeFlags) { this.flags = flags; + if (Debug.isDebugging) { + this.checker = checker; + } } function Signature() { @@ -2242,24 +2260,42 @@ namespace ts { export namespace Debug { export let currentAssertionLevel = AssertionLevel.None; + export let isDebugging = false; export function shouldAssert(level: AssertionLevel): boolean { return currentAssertionLevel >= level; } - export function assert(expression: boolean, message?: string, verboseDebugInfo?: () => string): void { + export function assert(expression: boolean, message?: string, verboseDebugInfo?: () => string, stackCrawlMark?: Function): void { if (!expression) { - let verboseDebugString = ""; if (verboseDebugInfo) { - verboseDebugString = "\r\nVerbose Debug Information: " + verboseDebugInfo(); + message += "\r\nVerbose Debug Information: " + verboseDebugInfo(); } - debugger; - throw new Error("Debug Failure. False expression: " + (message || "") + verboseDebugString); + fail(message ? "False expression: " + message : "False expression.", stackCrawlMark || assert); } } - export function fail(message?: string): void { - Debug.assert(/*expression*/ false, message); + export function fail(message?: string, stackCrawlMark?: Function): void { + debugger; + const e = new Error(message ? `Debug Failure. ` : "Debug Failure."); + if ((Error).captureStackTrace) { + (Error).captureStackTrace(e, stackCrawlMark || fail); + } + throw e; + } + + export function getFunctionName(func: Function) { + if (typeof func !== "function") { + return ""; + } + else if (func.hasOwnProperty("name")) { + return (func).name; + } + else { + const text = Function.prototype.toString.call(func); + const match = /^function\s+([\w\$]+)\s*\(/.exec(text); + return match ? match[1] : ""; + } } } @@ -2425,4 +2461,4 @@ namespace ts { export function isCheckJsEnabledForFile(sourceFile: SourceFile, compilerOptions: CompilerOptions) { return sourceFile.checkJsDirective ? sourceFile.checkJsDirective.enabled : compilerOptions.checkJs; } -} +} \ No newline at end of file diff --git a/src/compiler/factory.ts b/src/compiler/factory.ts index 63c2028c424..5d4457fdfd8 100644 --- a/src/compiler/factory.ts +++ b/src/compiler/factory.ts @@ -2130,6 +2130,24 @@ namespace ts { // Compound nodes + export function createImmediatelyInvokedFunctionExpression(statements: Statement[]): CallExpression; + export function createImmediatelyInvokedFunctionExpression(statements: Statement[], param: ParameterDeclaration, paramValue: Expression): CallExpression; + export function createImmediatelyInvokedFunctionExpression(statements: Statement[], param?: ParameterDeclaration, paramValue?: Expression) { + return createCall( + createFunctionExpression( + /*modifiers*/ undefined, + /*asteriskToken*/ undefined, + /*name*/ undefined, + /*typeParameters*/ undefined, + /*parameters*/ param ? [param] : [], + /*type*/ undefined, + createBlock(statements, /*multiLine*/ true) + ), + /*typeArguments*/ undefined, + /*argumentsArray*/ paramValue ? [paramValue] : [] + ); + } + export function createComma(left: Expression, right: Expression) { return createBinary(left, SyntaxKind.CommaToken, right); } @@ -3212,6 +3230,26 @@ namespace ts { return isBlock(node) ? node : setTextRange(createBlock([setTextRange(createReturn(node), node)], multiLine), node); } + export function convertFunctionDeclarationToExpression(node: FunctionDeclaration) { + Debug.assert(!!node.body); + const updated = createFunctionExpression( + node.modifiers, + node.asteriskToken, + node.name, + node.typeParameters, + node.parameters, + node.type, + node.body + ); + setOriginalNode(updated, node); + setTextRange(updated, node); + if (node.startsOnNewLine) { + updated.startsOnNewLine = true; + } + aggregateTransformFlags(updated); + return updated; + } + function isUseStrictPrologue(node: ExpressionStatement): boolean { return (node.expression as StringLiteral).text === "use strict"; } @@ -3610,7 +3648,7 @@ namespace ts { if (kind === SyntaxKind.FunctionExpression || kind === SyntaxKind.ArrowFunction) { const mutableCall = getMutableClone(emittedExpression); mutableCall.expression = setTextRange(createParen(callee), callee); - return recreatePartiallyEmittedExpressions(expression, mutableCall); + return recreateOuterExpressions(expression, mutableCall, OuterExpressionKinds.PartiallyEmittedExpressions); } } else { @@ -3652,22 +3690,6 @@ namespace ts { } } - /** - * Clones a series of not-emitted expressions with a new inner expression. - * - * @param originalOuterExpression The original outer expression. - * @param newInnerExpression The new inner expression. - */ - function recreatePartiallyEmittedExpressions(originalOuterExpression: Expression, newInnerExpression: Expression) { - if (isPartiallyEmittedExpression(originalOuterExpression)) { - const clone = getMutableClone(originalOuterExpression); - clone.expression = recreatePartiallyEmittedExpressions(clone.expression, newInnerExpression); - return clone; - } - - return newInnerExpression; - } - function getLeftmostExpression(node: Expression): Expression { while (true) { switch (node.kind) { @@ -3714,6 +3736,21 @@ namespace ts { All = Parentheses | Assertions | PartiallyEmittedExpressions } + export type OuterExpression = ParenthesizedExpression | TypeAssertion | AsExpression | PartiallyEmittedExpression; + + export function isOuterExpression(node: Node, kinds = OuterExpressionKinds.All): node is OuterExpression { + switch (node.kind) { + case SyntaxKind.ParenthesizedExpression: + return (kinds & OuterExpressionKinds.Parentheses) !== 0; + case SyntaxKind.TypeAssertionExpression: + case SyntaxKind.AsExpression: + return (kinds & OuterExpressionKinds.Assertions) !== 0; + case SyntaxKind.PartiallyEmittedExpression: + return (kinds & OuterExpressionKinds.PartiallyEmittedExpressions) !== 0; + } + return false; + } + export function skipOuterExpressions(node: Expression, kinds?: OuterExpressionKinds): Expression; export function skipOuterExpressions(node: Node, kinds?: OuterExpressionKinds): Node; export function skipOuterExpressions(node: Node, kinds = OuterExpressionKinds.All) { @@ -3767,6 +3804,25 @@ namespace ts { return node; } + function updateOuterExpression(outerExpression: OuterExpression, expression: Expression) { + switch (outerExpression.kind) { + case SyntaxKind.ParenthesizedExpression: return updateParen(outerExpression, expression); + case SyntaxKind.TypeAssertionExpression: return updateTypeAssertion(outerExpression, outerExpression.type, expression); + case SyntaxKind.AsExpression: return updateAsExpression(outerExpression, expression, outerExpression.type); + case SyntaxKind.PartiallyEmittedExpression: return updatePartiallyEmittedExpression(outerExpression, expression); + } + } + + export function recreateOuterExpressions(outerExpression: Expression | undefined, innerExpression: Expression, kinds = OuterExpressionKinds.All): Expression { + if (outerExpression && isOuterExpression(outerExpression, kinds)) { + return updateOuterExpression( + outerExpression, + recreateOuterExpressions(outerExpression.expression, innerExpression) + ); + } + return innerExpression; + } + export function startOnNewLine(node: T): T { node.startsOnNewLine = true; return node; diff --git a/src/compiler/sys.ts b/src/compiler/sys.ts index 7074abd3436..1abebe937e6 100644 --- a/src/compiler/sys.ts +++ b/src/compiler/sys.ts @@ -41,6 +41,7 @@ namespace ts { realpath?(path: string): string; /*@internal*/ getEnvironmentVariable(name: string): string; /*@internal*/ tryEnableSourceMapsForHost?(): void; + /*@internal*/ debugMode?: boolean; setTimeout?(callback: (...args: any[]) => void, ms: number, ...args: any[]): any; clearTimeout?(timeoutId: any): void; } @@ -428,6 +429,7 @@ namespace ts { realpath(path: string): string { return _fs.realpathSync(path); }, + debugMode: some(process.execArgv, arg => /^--(inspect|debug)(-brk)?(=\d+)?$/i.test(arg)), tryEnableSourceMapsForHost() { try { require("source-map-support").install(); @@ -517,4 +519,7 @@ namespace ts { ? AssertionLevel.Normal : AssertionLevel.None; } + if (sys && sys.debugMode) { + Debug.isDebugging = true; + } } diff --git a/src/compiler/transformers/es2015.ts b/src/compiler/transformers/es2015.ts index 63c10145165..4b9c577805e 100644 --- a/src/compiler/transformers/es2015.ts +++ b/src/compiler/transformers/es2015.ts @@ -343,7 +343,8 @@ namespace ts { return (node.transformFlags & TransformFlags.ContainsES2015) !== 0 || convertedLoopState !== undefined || (hierarchyFacts & HierarchyFacts.ConstructorWithCapturedSuper && isStatement(node)) - || (isIterationStatement(node, /*lookInLabeledStatements*/ false) && shouldConvertIterationStatementBody(node)); + || (isIterationStatement(node, /*lookInLabeledStatements*/ false) && shouldConvertIterationStatementBody(node)) + || isTypeScriptClassWrapper(node); } function visitor(node: Node): VisitResult { @@ -3251,6 +3252,10 @@ namespace ts { * @param node a CallExpression. */ function visitCallExpression(node: CallExpression) { + if (isTypeScriptClassWrapper(node)) { + return visitTypeScriptClassWrapper(node); + } + if (node.transformFlags & TransformFlags.ES2015) { return visitCallExpressionWithPotentialCapturedThisAssignment(node, /*assignToCapturedThis*/ true); } @@ -3262,6 +3267,147 @@ namespace ts { ); } + function visitTypeScriptClassWrapper(node: CallExpression) { + // This is a call to a class wrapper function (an IIFE) created by the 'ts' transformer. + // The wrapper has a form similar to: + // + // (function() { + // class C { // 1 + // } + // C.x = 1; // 2 + // return C; + // }()) + // + // When we transform the class, we end up with something like this: + // + // (function () { + // var C = (function () { // 3 + // function C() { + // } + // return C; // 4 + // }()); + // C.x = 1; + // return C; + // }()) + // + // We want to simplify the two nested IIFEs to end up with something like this: + // + // (function () { + // function C() { + // } + // C.x = 1; + // return C; + // }()) + + // We skip any outer expressions in a number of places to get to the innermost + // expression, but we will restore them later to preserve comments and source maps. + const body = cast(skipOuterExpressions(node.expression), isFunctionExpression).body; + + // The class statements are the statements generated by visiting the first statement of the + // body (1), while all other statements are added to remainingStatements (2) + const classStatements = visitNodes(body.statements, visitor, isStatement, 0, 1); + const remainingStatements = visitNodes(body.statements, visitor, isStatement, 1, body.statements.length - 1); + const varStatement = cast(firstOrUndefined(classStatements), isVariableStatement); + const variable = varStatement.declarationList.declarations[0]; + const initializer = skipOuterExpressions(variable.initializer); + + // Under certain conditions, the 'ts' transformer may may introduce a class alias, which + // we see as an assignment, for example: + // + // (function () { + // var C = C_1 = (function () { + // function C() { + // } + // C.x = function () { return C_1; } + // return C; + // }()); + // C = C_1 = __decorate([dec], C); + // return C; + // var C_1; + // }()) + // + const aliasAssignment = isAssignmentExpression(initializer) ? initializer : undefined; + + // The underlying call (3) is another IIFE that may contain a '_super' argument. + const call = cast(aliasAssignment ? skipOuterExpressions(aliasAssignment.right) : initializer, isCallExpression); + const func = cast(skipOuterExpressions(call.expression), isFunctionExpression); + + // When we extract the statements of the inner IIFE, we exclude the 'return' statement (4) + // as we already have one that has been introduced by the 'ts' transformer. + const funcStatements = func.body.statements.slice(0, -1); + + const statements: Statement[] = []; + if (aliasAssignment) { + // If we have a class alias assignment, we need to move it to the down-level constructor + // function we generated for the class. + const hasExtendsCall = isExpressionStatement(funcStatements[0]); + if (hasExtendsCall) { + statements.push(funcStatements[0]); + } + + // We reuse the comment and source-map positions from the original variable statement + // and class alias, while converting the function declaration for the class constructor + // into an expression. + statements.push( + updateVariableStatement( + varStatement, + /*modifiers*/ undefined, + updateVariableDeclarationList(varStatement.declarationList, [ + updateVariableDeclaration(variable, + variable.name, + /*type*/ undefined, + updateBinary(aliasAssignment, + aliasAssignment.left, + convertFunctionDeclarationToExpression( + cast(funcStatements[hasExtendsCall ? 1 : 0], isFunctionDeclaration) + ) + ) + ) + ]) + ) + ); + + addRange(statements, funcStatements.slice(hasExtendsCall ? 2 : 1)); + } + else { + addRange(statements, funcStatements); + } + + addRange(statements, remainingStatements); + + // The 'es2015' class transform may add an end-of-declaration marker. If so we will add it + // after the remaining statements from the 'ts' transformer. + addRange(statements, classStatements.slice(1)); + + // Recreate any outer parentheses or partially-emitted expressions to preserve source map + // and comment locations. + return recreateOuterExpressions(node.expression, + recreateOuterExpressions(variable.initializer, + recreateOuterExpressions(aliasAssignment && aliasAssignment.right, + updateCall(call, + recreateOuterExpressions(call.expression, + updateFunctionExpression( + func, + /*modifiers*/ undefined, + /*asteriskToken*/ undefined, + /*name*/ undefined, + /*typeParameters*/ undefined, + func.parameters, + /*type*/ undefined, + updateBlock( + func.body, + statements + ) + ) + ), + /*typeArguments*/ undefined, + call.arguments + ) + ) + ) + ); + } + function visitImmediateSuperCallInBody(node: CallExpression) { return visitCallExpressionWithPotentialCapturedThisAssignment(node, /*assignToCapturedThis*/ false); } @@ -3807,8 +3953,7 @@ namespace ts { } if (isClassElement(currentNode) && currentNode.parent === declaration) { // we are in the class body, but we treat static fields as outside of the class body - return currentNode.kind !== SyntaxKind.PropertyDeclaration - || (getModifierFlags(currentNode) & ModifierFlags.Static) === 0; + return true; } currentNode = currentNode.parent; } diff --git a/src/compiler/transformers/ts.ts b/src/compiler/transformers/ts.ts index cc7f89acfb8..876a7ff2d72 100644 --- a/src/compiler/transformers/ts.ts +++ b/src/compiler/transformers/ts.ts @@ -18,6 +18,22 @@ namespace ts { NonQualifiedEnumMembers = 1 << 3 } + const enum ClassFacts { + HasStaticInitializedProperties = 1 << 0, + HasConstructorDecorators = 1 << 1, + HasMemberDecorators = 1 << 2, + IsNamespaceExport = 1 << 3, + IsNamedExternalExport = 1 << 4, + IsDefaultExternalExport = 1 << 5, + HasExtendsClause = 1 << 6, + UseImmediatelyInvokedFunctionExpression = 1 << 7, + + HasAnyDecorators = HasConstructorDecorators | HasMemberDecorators, + NeedsName = HasStaticInitializedProperties | HasMemberDecorators, + MayNeedImmediatelyInvokedFunctionExpression = HasAnyDecorators | HasStaticInitializedProperties, + IsExported = IsNamespaceExport | IsDefaultExternalExport | IsNamedExternalExport, + } + export function transformTypeScript(context: TransformationContext) { const { startLexicalEnvironment, @@ -502,6 +518,19 @@ namespace ts { return parameter.decorators !== undefined && parameter.decorators.length > 0; } + function getClassFacts(node: ClassDeclaration, staticProperties: PropertyDeclaration[]) { + let facts: ClassFacts = 0; + if (some(staticProperties)) facts |= ClassFacts.HasStaticInitializedProperties; + if (getClassExtendsHeritageClauseElement(node)) facts |= ClassFacts.HasExtendsClause; + if (shouldEmitDecorateCallForClass(node)) facts |= ClassFacts.HasConstructorDecorators; + if (childIsDecorated(node)) facts |= ClassFacts.HasMemberDecorators; + if (isNamespaceExport(node)) facts |= ClassFacts.IsNamespaceExport; + if ((facts & ClassFacts.IsExported) === 0 && isDefaultExternalModuleExport(node)) facts |= ClassFacts.IsDefaultExternalExport; + if ((facts & ClassFacts.IsExported) === 0 && isNamedExternalModuleExport(node)) facts |= ClassFacts.IsNamedExternalExport; + if (languageVersion <= ScriptTarget.ES5 && (facts & ClassFacts.MayNeedImmediatelyInvokedFunctionExpression)) facts |= ClassFacts.UseImmediatelyInvokedFunctionExpression; + return facts; + } + /** * Transforms a class declaration with TypeScript syntax into compatible ES6. * @@ -515,32 +544,26 @@ namespace ts { */ function visitClassDeclaration(node: ClassDeclaration): VisitResult { const staticProperties = getInitializedProperties(node, /*isStatic*/ true); - const hasExtendsClause = getClassExtendsHeritageClauseElement(node) !== undefined; - const isDecoratedClass = shouldEmitDecorateCallForClass(node); + const facts = getClassFacts(node, staticProperties); - // emit name if - // - node has a name - // - node has static initializers - // - node has a member that is decorated - // - let name = node.name; - if (!name && (staticProperties.length > 0 || childIsDecorated(node))) { - name = getGeneratedNameForNode(node); + if (facts & ClassFacts.UseImmediatelyInvokedFunctionExpression) { + context.startLexicalEnvironment(); } - const classStatement = isDecoratedClass - ? createClassDeclarationHeadWithDecorators(node, name, hasExtendsClause) - : createClassDeclarationHeadWithoutDecorators(node, name, hasExtendsClause, staticProperties.length > 0); + const name = node.name || (facts & ClassFacts.NeedsName ? getGeneratedNameForNode(node) : undefined); + const classStatement = facts & ClassFacts.HasConstructorDecorators + ? createClassDeclarationHeadWithDecorators(node, name, facts) + : createClassDeclarationHeadWithoutDecorators(node, name, facts); - const statements: Statement[] = [classStatement]; + let statements: Statement[] = [classStatement]; // Emit static property assignment. Because classDeclaration is lexically evaluated, // it is safe to emit static property assignment after classDeclaration // From ES6 specification: // HasLexicalDeclaration (N) : Determines if the argument identifier has a binding in this environment record that was created using // a lexical declaration such as a LexicalDeclaration or a ClassDeclaration. - if (staticProperties.length) { - addInitializedPropertyStatements(statements, staticProperties, getLocalName(node)); + if (facts & ClassFacts.HasStaticInitializedProperties) { + addInitializedPropertyStatements(statements, staticProperties, facts & ClassFacts.UseImmediatelyInvokedFunctionExpression ? getInternalName(node) : getLocalName(node)); } // Write any decorators of the node. @@ -548,17 +571,52 @@ namespace ts { addClassElementDecorationStatements(statements, node, /*isStatic*/ true); addConstructorDecorationStatement(statements, node); + if (facts & ClassFacts.UseImmediatelyInvokedFunctionExpression) { + const closingBraceLocation = createTokenRange(skipTrivia(currentSourceFile.text, node.members.end), SyntaxKind.CloseBraceToken); + const localName = getInternalName(node); + + // The following partially-emitted expression exists purely to align our sourcemap + // emit with the original emitter. + const outer = createPartiallyEmittedExpression(localName); + outer.end = closingBraceLocation.end; + setEmitFlags(outer, EmitFlags.NoComments); + + const statement = createReturn(outer); + statement.pos = closingBraceLocation.pos; + setEmitFlags(statement, EmitFlags.NoComments | EmitFlags.NoTokenSourceMaps); + statements.push(statement); + + addRange(statements, context.endLexicalEnvironment()); + + const varStatement = createVariableStatement( + /*modifiers*/ undefined, + createVariableDeclarationList([ + createVariableDeclaration( + getLocalName(node, /*allowComments*/ false, /*allowSourceMaps*/ false), + /*type*/ undefined, + createImmediatelyInvokedFunctionExpression(statements) + ) + ]) + ); + + setOriginalNode(varStatement, node); + setCommentRange(varStatement, node); + setSourceMapRange(varStatement, moveRangePastDecorators(node)); + startOnNewLine(varStatement); + statements = [varStatement]; + } + // If the class is exported as part of a TypeScript namespace, emit the namespace export. // Otherwise, if the class was exported at the top level and was decorated, emit an export // declaration or export default for the class. - if (isNamespaceExport(node)) { + if (facts & ClassFacts.IsNamespaceExport) { addExportMemberAssignment(statements, node); } - else if (isDecoratedClass) { - if (isDefaultExternalModuleExport(node)) { + else if (facts & ClassFacts.UseImmediatelyInvokedFunctionExpression || facts & ClassFacts.HasConstructorDecorators) { + if (facts & ClassFacts.IsDefaultExternalExport) { statements.push(createExportDefault(getLocalName(node, /*allowComments*/ false, /*allowSourceMaps*/ true))); } - else if (isNamedExternalModuleExport(node)) { + else if (facts & ClassFacts.IsNamedExternalExport) { statements.push(createExternalModuleExport(getLocalName(node, /*allowComments*/ false, /*allowSourceMaps*/ true))); } } @@ -577,26 +635,31 @@ namespace ts { * * @param node A ClassDeclaration node. * @param name The name of the class. - * @param hasExtendsClause A value indicating whether the class has an extends clause. - * @param hasStaticProperties A value indicating whether the class has static properties. + * @param facts Precomputed facts about the class. */ - function createClassDeclarationHeadWithoutDecorators(node: ClassDeclaration, name: Identifier, hasExtendsClause: boolean, hasStaticProperties: boolean) { + function createClassDeclarationHeadWithoutDecorators(node: ClassDeclaration, name: Identifier, facts: ClassFacts) { // ${modifiers} class ${name} ${heritageClauses} { // ${members} // } + + // we do not emit modifiers on the declaration if we are emitting an IIFE + const modifiers = !(facts & ClassFacts.UseImmediatelyInvokedFunctionExpression) + ? visitNodes(node.modifiers, modifierVisitor, isModifier) + : undefined; + const classDeclaration = createClassDeclaration( /*decorators*/ undefined, - visitNodes(node.modifiers, modifierVisitor, isModifier), + modifiers, name, /*typeParameters*/ undefined, visitNodes(node.heritageClauses, visitor, isHeritageClause), - transformClassMembers(node, hasExtendsClause) + transformClassMembers(node, (facts & ClassFacts.HasExtendsClause) !== 0) ); // To better align with the old emitter, we should not emit a trailing source map // entry if the class has static properties. let emitFlags = getEmitFlags(node); - if (hasStaticProperties) { + if (facts & ClassFacts.HasStaticInitializedProperties) { emitFlags |= EmitFlags.NoTrailingSourceMap; } @@ -613,9 +676,9 @@ namespace ts { * @param statements A statement list to which to add the declaration. * @param node A ClassDeclaration node. * @param name The name of the class. - * @param hasExtendsClause A value indicating whether the class has an extends clause. + * @param facts Precomputed facts about the clas. */ - function createClassDeclarationHeadWithDecorators(node: ClassDeclaration, name: Identifier, hasExtendsClause: boolean) { + function createClassDeclarationHeadWithDecorators(node: ClassDeclaration, name: Identifier, facts: ClassFacts) { // When we emit an ES6 class that has a class decorator, we must tailor the // emit to certain specific cases. // @@ -710,7 +773,7 @@ namespace ts { // ${members} // } const heritageClauses = visitNodes(node.heritageClauses, visitor, isHeritageClause); - const members = transformClassMembers(node, hasExtendsClause); + const members = transformClassMembers(node, (facts & ClassFacts.HasExtendsClause) !== 0); const classExpression = createClassExpression(/*modifiers*/ undefined, name, /*typeParameters*/ undefined, heritageClauses, members); setOriginalNode(classExpression, node); setTextRange(classExpression, location); diff --git a/src/compiler/types.ts b/src/compiler/types.ts index a623da1f461..7b830d4c5ce 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -3074,6 +3074,7 @@ namespace ts { export interface Type { flags: TypeFlags; // Flags /* @internal */ id: number; // Unique ID + /* @internal */ checker: TypeChecker; symbol?: Symbol; // Symbol associated with type (if any) pattern?: DestructuringPattern; // Destructuring pattern represented by type (if any) aliasSymbol?: Symbol; // Alias associated with type @@ -3977,34 +3978,34 @@ namespace ts { } export const enum EmitFlags { - SingleLine = 1 << 0, // The contents of this node should be emitted on a single line. - AdviseOnEmitNode = 1 << 1, // The printer should invoke the onEmitNode callback when printing this node. - NoSubstitution = 1 << 2, // Disables further substitution of an expression. - CapturesThis = 1 << 3, // The function captures a lexical `this` - NoLeadingSourceMap = 1 << 4, // Do not emit a leading source map location for this node. - NoTrailingSourceMap = 1 << 5, // Do not emit a trailing source map location for this node. + SingleLine = 1 << 0, // The contents of this node should be emitted on a single line. + AdviseOnEmitNode = 1 << 1, // The printer should invoke the onEmitNode callback when printing this node. + NoSubstitution = 1 << 2, // Disables further substitution of an expression. + CapturesThis = 1 << 3, // The function captures a lexical `this` + NoLeadingSourceMap = 1 << 4, // Do not emit a leading source map location for this node. + NoTrailingSourceMap = 1 << 5, // Do not emit a trailing source map location for this node. NoSourceMap = NoLeadingSourceMap | NoTrailingSourceMap, // Do not emit a source map location for this node. - NoNestedSourceMaps = 1 << 6, // Do not emit source map locations for children of this node. - NoTokenLeadingSourceMaps = 1 << 7, // Do not emit leading source map location for token nodes. - NoTokenTrailingSourceMaps = 1 << 8, // Do not emit trailing source map location for token nodes. + NoNestedSourceMaps = 1 << 6, // Do not emit source map locations for children of this node. + NoTokenLeadingSourceMaps = 1 << 7, // Do not emit leading source map location for token nodes. + NoTokenTrailingSourceMaps = 1 << 8, // Do not emit trailing source map location for token nodes. NoTokenSourceMaps = NoTokenLeadingSourceMaps | NoTokenTrailingSourceMaps, // Do not emit source map locations for tokens of this node. - NoLeadingComments = 1 << 9, // Do not emit leading comments for this node. - NoTrailingComments = 1 << 10, // Do not emit trailing comments for this node. + NoLeadingComments = 1 << 9, // Do not emit leading comments for this node. + NoTrailingComments = 1 << 10, // Do not emit trailing comments for this node. NoComments = NoLeadingComments | NoTrailingComments, // Do not emit comments for this node. NoNestedComments = 1 << 11, HelperName = 1 << 12, - ExportName = 1 << 13, // Ensure an export prefix is added for an identifier that points to an exported declaration with a local name (see SymbolFlags.ExportHasLocal). - LocalName = 1 << 14, // Ensure an export prefix is not added for an identifier that points to an exported declaration. - InternalName = 1 << 15, // The name is internal to an ES5 class body function. - Indented = 1 << 16, // Adds an explicit extra indentation level for class and function bodies when printing (used to match old emitter). - NoIndentation = 1 << 17, // Do not indent the node. + ExportName = 1 << 13, // Ensure an export prefix is added for an identifier that points to an exported declaration with a local name (see SymbolFlags.ExportHasLocal). + LocalName = 1 << 14, // Ensure an export prefix is not added for an identifier that points to an exported declaration. + InternalName = 1 << 15, // The name is internal to an ES5 class body function. + Indented = 1 << 16, // Adds an explicit extra indentation level for class and function bodies when printing (used to match old emitter). + NoIndentation = 1 << 17, // Do not indent the node. AsyncFunctionBody = 1 << 18, - ReuseTempVariableScope = 1 << 19, // Reuse the existing temp variable scope during emit. - CustomPrologue = 1 << 20, // Treat the statement as if it were a prologue directive (NOTE: Prologue directives are *not* transformed). - NoHoisting = 1 << 21, // Do not hoist this declaration in --module system - HasEndOfDeclarationMarker = 1 << 22, // Declaration has an associated NotEmittedStatement to mark the end of the declaration - Iterator = 1 << 23, // The expression to a `yield*` should be treated as an Iterator when down-leveling, not an Iterable. - NoAsciiEscaping = 1 << 24, // When synthesizing nodes that lack an original node or textSourceNode, we want to write the text on the node with ASCII escaping substitutions. + ReuseTempVariableScope = 1 << 19, // Reuse the existing temp variable scope during emit. + CustomPrologue = 1 << 20, // Treat the statement as if it were a prologue directive (NOTE: Prologue directives are *not* transformed). + NoHoisting = 1 << 21, // Do not hoist this declaration in --module system + HasEndOfDeclarationMarker = 1 << 22, // Declaration has an associated NotEmittedStatement to mark the end of the declaration + Iterator = 1 << 23, // The expression to a `yield*` should be treated as an Iterator when down-leveling, not an Iterable. + NoAsciiEscaping = 1 << 24, // When synthesizing nodes that lack an original node or textSourceNode, we want to write the text on the node with ASCII escaping substitutions. } export interface EmitHelper { diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 2b6831f8814..b5d3fe348d9 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -850,10 +850,88 @@ namespace ts { return node && (node.kind === SyntaxKind.GetAccessor || node.kind === SyntaxKind.SetAccessor); } - export function isClassLike(node: Node): node is ClassLikeDeclaration { + export function isClassLike(node: Node | undefined): node is ClassLikeDeclaration { return node && (node.kind === SyntaxKind.ClassDeclaration || node.kind === SyntaxKind.ClassExpression); } + export function isImmediatelyInvokedFunctionExpression(node: Node) { + if (!isCallExpression(node) || + some(node.typeArguments) || + some(node.arguments)) { + return false; + } + const expression = skipParentheses(node.expression); + if (!isFunctionExpression(expression) || + some(expression.typeParameters) || + some(expression.parameters) || + expression.type || + !expression.body) { + return false; + } + return true; + } + + export function isTypeScriptClassWrapper(node: Node) { + if (!isImmediatelyInvokedFunctionExpression(node) || + isParseTreeNode(node)) { + return false; + } + + const func = skipParentheses((node).expression); + if (isParseTreeNode(func)) { + return false; + } + + const statements = func.body.statements; + if (statements.length < 2) { + return false; + } + + const firstStatement = statements[0]; + if (isParseTreeNode(firstStatement) || + !isClassLike(firstStatement) && + !isClassLikeVariableStatement(firstStatement)) { + return false; + } + + const returnStatement = tryCast(elementAt(statements, isVariableStatement(lastOrUndefined(statements)) ? -2 : -1), isReturnStatement); + if (!isReturnStatement(returnStatement) || + !returnStatement.expression || + !isIdentifier(skipOuterExpressions(returnStatement.expression))) { + return false; + } + + return true; + } + + function isClassLikeVariableStatement(node: Node) { + if (!isVariableStatement(node)) return false; + const variable = singleOrUndefined((node).declarationList.declarations); + return variable + && variable.initializer + && isIdentifier(variable.name) + && (isClassLike(variable.initializer) + || (isAssignmentExpression(variable.initializer) + && isIdentifier(variable.initializer.left) + && isClassLike(variable.initializer.right))); + } + + export function isExpressionStatement(node: Node): node is ExpressionStatement { + return node.kind === SyntaxKind.ExpressionStatement; + } + + export function isReturnStatement(node: Node): node is ReturnStatement { + return node.kind === SyntaxKind.ReturnStatement; + } + + export function isFunctionExpression(node: Node): node is FunctionExpression { + return node.kind === SyntaxKind.FunctionExpression; + } + + export function isFunctionDeclaration(node: Node): node is FunctionDeclaration { + return node.kind === SyntaxKind.FunctionDeclaration; + } + export function isFunctionLike(node: Node): node is FunctionLikeDeclaration { return node && isFunctionLikeKind(node.kind); } @@ -3051,6 +3129,13 @@ namespace ts { return node.modifierFlagsCache & ~ModifierFlags.HasComputedFlags; } + const flags = getModifierFlagsNoCache(node); + node.modifierFlagsCache = flags | ModifierFlags.HasComputedFlags; + return flags; + } + + export function getModifierFlagsNoCache(node: Node): ModifierFlags { + let flags = ModifierFlags.None; if (node.modifiers) { for (const modifier of node.modifiers) { @@ -3062,7 +3147,6 @@ namespace ts { flags |= ModifierFlags.Export; } - node.modifierFlagsCache = flags | ModifierFlags.HasComputedFlags; return flags; } @@ -3351,27 +3435,104 @@ namespace ts { return false; } + /** + * Formats an enum value as a string for debugging and debug assertions. + */ + function formatEnum(value = 0, enumObject: any, isFlags: boolean, formatCache?: string[]) { + const cached = formatCache && formatCache[value]; + if (cached !== undefined) { + return cached; + } + const result = isFlags ? formatFlagsEnum(value, enumObject) : getEnumName(value, enumObject); + if (formatCache) { + formatCache[value] = result; + } + return result; + } + + /** + * Gets the name for an enum value for debugging and debug assertions. + */ + function getEnumName(value: number, enumObject: any) { + for (const name in enumObject) { + if (enumObject[name] === value) { + return name; + } + } + return value.toString(); + } + + /** + * Formats the bitwise flag values of an enum value for debugging and debug assertions. + */ + function formatFlagsEnum(value: number, enumObject: any) { + const members = getEnumMembers(enumObject); + let result = ""; + if (value === 0) { + return members.length > 0 && members[0][0] === 0 ? members[0][1] : "0"; + } + + let remainingFlags = value; + for (let i = members.length - 1; i >= 0 && remainingFlags !== 0; i--) { + const [enumValue, enumName] = members[i]; + if (enumValue !== 0 && (remainingFlags & enumValue) === enumValue) { + remainingFlags &= ~enumValue; + result = `${enumName}${result ? ", " : ""}${result}`; + } + } + + if (remainingFlags === 0) { + return result; + } + + return value.toString(); + } + + function getEnumMembers(enumObject: any) { + const result: [number, string][] = []; + for (const name in enumObject) { + const value = enumObject[name]; + if (typeof value === "number") { + result.push([value, name]); + } + } + + return stableSort(result, (x, y) => compareValues(x[0], y[0])); + } + const syntaxKindCache: string[] = []; - export function formatSyntaxKind(kind: SyntaxKind): string { - const syntaxKindEnum = (ts).SyntaxKind; - if (syntaxKindEnum) { - const cached = syntaxKindCache[kind]; - if (cached !== undefined) { - return cached; - } + return formatEnum(kind, (ts).SyntaxKind, /*isFlags*/ false, syntaxKindCache); + } - for (const name in syntaxKindEnum) { - if (syntaxKindEnum[name] === kind) { - const result = `${kind} (${name})`; - syntaxKindCache[kind] = result; - return result; - } - } - } - else { - return kind.toString(); - } + const modifierFlagsCache: string[] = []; + export function formatModifierFlags(flags: ModifierFlags): string { + return formatEnum(flags, (ts).ModifierFlags, /*isFlags*/ true, modifierFlagsCache); + } + + const transformFlagsCache: string[] = []; + export function formatTransformFlags(flags: TransformFlags): string { + return formatEnum(flags, (ts).TransformFlags, /*isFlags*/ true, transformFlagsCache); + } + + const emitFlagsCache: string[] = []; + export function formatEmitFlags(flags: EmitFlags): string { + return formatEnum(flags, (ts).EmitFlags, /*isFlags*/ true, emitFlagsCache); + } + + const symbolFlagsCache: string[] = []; + export function formatSymbolFlags(flags: SymbolFlags): string { + return formatEnum(flags, (ts).SymbolFlags, /*isFlags*/ true, symbolFlagsCache); + } + + const typeFlagsCache: string[] = []; + export function formatTypeFlags(flags: TypeFlags): string { + return formatEnum(flags, (ts).TypeFlags, /*isFlags*/ true, typeFlagsCache); + } + + const objectFlagsCache: string[] = []; + export function formatObjectFlags(flags: ObjectFlags): string { + return formatEnum(flags, (ts).ObjectFlags, /*isFlags*/ true, objectFlagsCache); } export function getRangePos(range: TextRange | undefined) { @@ -3858,6 +4019,10 @@ namespace ts { return node.kind === SyntaxKind.CallExpression; } + export function isParethesizedExpression(node: Node): node is ParenthesizedExpression { + return node.kind === SyntaxKind.ParenthesizedExpression; + } + export function isTemplateLiteral(node: Node): node is TemplateLiteral { const kind = node.kind; return kind === SyntaxKind.TemplateExpression @@ -3984,6 +4149,10 @@ namespace ts { || isExpression(node); } + export function isVariableStatement(node: Node): node is VariableStatement { + return node.kind === SyntaxKind.VariableStatement; + } + export function isVariableDeclaration(node: Node): node is VariableDeclaration { return node.kind === SyntaxKind.VariableDeclaration; } diff --git a/src/compiler/visitor.ts b/src/compiler/visitor.ts index eb28721a142..208c99c6585 100644 --- a/src/compiler/visitor.ts +++ b/src/compiler/visitor.ts @@ -1514,57 +1514,80 @@ namespace ts { } export namespace Debug { + if (isDebugging) { + // Add additional properties in debug mode to assist with debugging. + Object.defineProperties(objectAllocator.getSymbolConstructor().prototype, { + "__debugFlags": { get(this: Symbol) { return formatSymbolFlags(this.flags); } } + }); + + Object.defineProperties(objectAllocator.getTypeConstructor().prototype, { + "__debugFlags": { get(this: Type) { return formatTypeFlags(this.flags); } }, + "__debugObjectFlags": { get(this: Type) { return this.flags & TypeFlags.Object ? formatObjectFlags((this).objectFlags) : ""; } }, + "__debugTypeToString": { value(this: Type) { return this.checker.typeToString(this); } }, + }); + + for (const ctor of [objectAllocator.getNodeConstructor(), objectAllocator.getIdentifierConstructor(), objectAllocator.getTokenConstructor(), objectAllocator.getSourceFileConstructor()]) { + if (!ctor.prototype.hasOwnProperty("__debugKind")) { + Object.defineProperties(ctor.prototype, { + "__debugKind": { get(this: Node) { return formatSyntaxKind(this.kind); } }, + "__debugModifierFlags": { get(this: Node) { return formatModifierFlags(getModifierFlagsNoCache(this)); } }, + "__debugTransformFlags": { get(this: Node) { return formatTransformFlags(this.transformFlags); } }, + "__debugEmitFlags": { get(this: Node) { return formatEmitFlags(getEmitFlags(this)); } }, + "__debugGetText": { value(this: Node, includeTrivia?: boolean) { + if (nodeIsSynthesized(this)) return ""; + const parseNode = getParseTreeNode(this); + const sourceFile = parseNode && getSourceFileOfNode(parseNode); + return sourceFile ? getSourceTextOfNodeFromSourceFile(sourceFile, parseNode, includeTrivia) : ""; + } } + }); + } + } + } + export const failBadSyntaxKind = shouldAssert(AssertionLevel.Normal) - ? (node: Node, message?: string) => assert(false, message || "Unexpected node.", () => `Node ${formatSyntaxKind(node.kind)} was unexpected.`) + ? (node: Node, message?: string): void => fail( + `${message || "Unexpected node."}\r\nNode ${formatSyntaxKind(node.kind)} was unexpected.`, + failBadSyntaxKind) : noop; export const assertEachNode = shouldAssert(AssertionLevel.Normal) - ? (nodes: Node[], test: (node: Node) => boolean, message?: string) => assert( - test === undefined || every(nodes, test), - message || "Unexpected node.", - () => `Node array did not pass test '${getFunctionName(test)}'.`) + ? (nodes: Node[], test: (node: Node) => boolean, message?: string): void => assert( + test === undefined || every(nodes, test), + message || "Unexpected node.", + () => `Node array did not pass test '${getFunctionName(test)}'.`, + assertEachNode) : noop; export const assertNode = shouldAssert(AssertionLevel.Normal) - ? (node: Node, test: (node: Node) => boolean, message?: string) => assert( - test === undefined || test(node), - message || "Unexpected node.", - () => `Node ${formatSyntaxKind(node.kind)} did not pass test '${getFunctionName(test)}'.`) + ? (node: Node, test: (node: Node) => boolean, message?: string): void => assert( + test === undefined || test(node), + message || "Unexpected node.", + () => `Node ${formatSyntaxKind(node.kind)} did not pass test '${getFunctionName(test)}'.`, + assertNode) : noop; export const assertOptionalNode = shouldAssert(AssertionLevel.Normal) - ? (node: Node, test: (node: Node) => boolean, message?: string) => assert( - test === undefined || node === undefined || test(node), - message || "Unexpected node.", - () => `Node ${formatSyntaxKind(node.kind)} did not pass test '${getFunctionName(test)}'.`) + ? (node: Node, test: (node: Node) => boolean, message?: string): void => assert( + test === undefined || node === undefined || test(node), + message || "Unexpected node.", + () => `Node ${formatSyntaxKind(node.kind)} did not pass test '${getFunctionName(test)}'.`, + assertOptionalNode) : noop; export const assertOptionalToken = shouldAssert(AssertionLevel.Normal) - ? (node: Node, kind: SyntaxKind, message?: string) => assert( - kind === undefined || node === undefined || node.kind === kind, - message || "Unexpected node.", - () => `Node ${formatSyntaxKind(node.kind)} was not a '${formatSyntaxKind(kind)}' token.`) + ? (node: Node, kind: SyntaxKind, message?: string): void => assert( + kind === undefined || node === undefined || node.kind === kind, + message || "Unexpected node.", + () => `Node ${formatSyntaxKind(node.kind)} was not a '${formatSyntaxKind(kind)}' token.`, + assertOptionalToken) : noop; export const assertMissingNode = shouldAssert(AssertionLevel.Normal) - ? (node: Node, message?: string) => assert( - node === undefined, - message || "Unexpected node.", - () => `Node ${formatSyntaxKind(node.kind)} was unexpected'.`) + ? (node: Node, message?: string): void => assert( + node === undefined, + message || "Unexpected node.", + () => `Node ${formatSyntaxKind(node.kind)} was unexpected'.`, + assertMissingNode) : noop; - - function getFunctionName(func: Function) { - if (typeof func !== "function") { - return ""; - } - else if (func.hasOwnProperty("name")) { - return (func).name; - } - else { - const text = Function.prototype.toString.call(func); - const match = /^function\s+([\w\$]+)\s*\(/.exec(text); - return match ? match[1] : ""; - } - } } } diff --git a/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndExportedVarThatShareAName.js b/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndExportedVarThatShareAName.js index cb2f7c6cb77..05f14d26369 100644 --- a/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndExportedVarThatShareAName.js +++ b/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndExportedVarThatShareAName.js @@ -28,9 +28,9 @@ var Point = (function () { this.x = x; this.y = y; } + Point.Origin = { x: 0, y: 0 }; return Point; }()); -Point.Origin = { x: 0, y: 0 }; (function (Point) { Point.Origin = ""; //expected duplicate identifier error })(Point || (Point = {})); @@ -41,9 +41,9 @@ var A; this.x = x; this.y = y; } + Point.Origin = { x: 0, y: 0 }; return Point; }()); - Point.Origin = { x: 0, y: 0 }; A.Point = Point; (function (Point) { Point.Origin = ""; //expected duplicate identifier error diff --git a/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndNonExportedVarThatShareAName.js b/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndNonExportedVarThatShareAName.js index ef77d6257fb..90c7523b931 100644 --- a/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndNonExportedVarThatShareAName.js +++ b/tests/baselines/reference/ClassAndModuleThatMergeWithStaticVariableAndNonExportedVarThatShareAName.js @@ -28,9 +28,9 @@ var Point = (function () { this.x = x; this.y = y; } + Point.Origin = { x: 0, y: 0 }; return Point; }()); -Point.Origin = { x: 0, y: 0 }; (function (Point) { var Origin = ""; // not an error, since not exported })(Point || (Point = {})); @@ -41,9 +41,9 @@ var A; this.x = x; this.y = y; } + Point.Origin = { x: 0, y: 0 }; return Point; }()); - Point.Origin = { x: 0, y: 0 }; A.Point = Point; (function (Point) { var Origin = ""; // not an error since not exported diff --git a/tests/baselines/reference/ClassDeclarationWithInvalidConstOnPropertyDeclaration.js b/tests/baselines/reference/ClassDeclarationWithInvalidConstOnPropertyDeclaration.js index 7633955b227..d5c3b3d63f4 100644 --- a/tests/baselines/reference/ClassDeclarationWithInvalidConstOnPropertyDeclaration.js +++ b/tests/baselines/reference/ClassDeclarationWithInvalidConstOnPropertyDeclaration.js @@ -7,6 +7,6 @@ class AtomicNumbers { var AtomicNumbers = (function () { function AtomicNumbers() { } + AtomicNumbers.H = 1; return AtomicNumbers; }()); -AtomicNumbers.H = 1; diff --git a/tests/baselines/reference/amdImportNotAsPrimaryExpression.js b/tests/baselines/reference/amdImportNotAsPrimaryExpression.js index 651ae7a6d39..40bb07fa9c3 100644 --- a/tests/baselines/reference/amdImportNotAsPrimaryExpression.js +++ b/tests/baselines/reference/amdImportNotAsPrimaryExpression.js @@ -39,9 +39,9 @@ define(["require", "exports"], function (require, exports) { function C1() { this.m1 = 42; } + C1.s1 = true; return C1; }()); - C1.s1 = true; exports.C1 = C1; var E1; (function (E1) { diff --git a/tests/baselines/reference/autolift4.js b/tests/baselines/reference/autolift4.js index 6d91c61d59d..d784798358e 100644 --- a/tests/baselines/reference/autolift4.js +++ b/tests/baselines/reference/autolift4.js @@ -42,9 +42,9 @@ var Point = (function () { Point.prototype.getDist = function () { return Math.sqrt(this.x * this.x + this.y * this.y); }; + Point.origin = new Point(0, 0); return Point; }()); -Point.origin = new Point(0, 0); var Point3D = (function (_super) { __extends(Point3D, _super); function Point3D(x, y, z, m) { diff --git a/tests/baselines/reference/blockScopedNamespaceDifferentFile.js b/tests/baselines/reference/blockScopedNamespaceDifferentFile.js index 3eab7477c09..82d72e466e1 100644 --- a/tests/baselines/reference/blockScopedNamespaceDifferentFile.js +++ b/tests/baselines/reference/blockScopedNamespaceDifferentFile.js @@ -27,9 +27,9 @@ var C; var Name = (function () { function Name(parameters) { } + Name.funcData = A.AA.func(); + Name.someConst = A.AA.foo; return Name; }()); - Name.funcData = A.AA.func(); - Name.someConst = A.AA.foo; C.Name = Name; })(C || (C = {})); diff --git a/tests/baselines/reference/blockScopedVariablesUseBeforeDef.js b/tests/baselines/reference/blockScopedVariablesUseBeforeDef.js index 0197d919fef..619ee51ce75 100644 --- a/tests/baselines/reference/blockScopedVariablesUseBeforeDef.js +++ b/tests/baselines/reference/blockScopedVariablesUseBeforeDef.js @@ -177,9 +177,9 @@ function foo10() { var A = (function () { function A() { } + A.a = x; return A; }()); - A.a = x; var x; } function foo11() { diff --git a/tests/baselines/reference/class2.js b/tests/baselines/reference/class2.js index 91ac89da109..6ef78ed46ee 100644 --- a/tests/baselines/reference/class2.js +++ b/tests/baselines/reference/class2.js @@ -5,6 +5,6 @@ class foo { constructor() { static f = 3; } } var foo = (function () { function foo() { } + foo.f = 3; return foo; }()); -foo.f = 3; diff --git a/tests/baselines/reference/classBlockScoping.js b/tests/baselines/reference/classBlockScoping.js index 76d0dd892de..3cae2d3cb7d 100644 --- a/tests/baselines/reference/classBlockScoping.js +++ b/tests/baselines/reference/classBlockScoping.js @@ -62,9 +62,9 @@ function f(b) { Foo.prototype.m = function () { new Foo(); }; + Foo.y = new Foo(); return Foo; }()); - Foo_1.y = new Foo_1(); new Foo_1(); } var _a; diff --git a/tests/baselines/reference/classExpressionWithDecorator1.js b/tests/baselines/reference/classExpressionWithDecorator1.js index 9b52891b559..e051e05251b 100644 --- a/tests/baselines/reference/classExpressionWithDecorator1.js +++ b/tests/baselines/reference/classExpressionWithDecorator1.js @@ -12,10 +12,10 @@ var v = ; var C = (function () { function C() { } + C.p = 1; + C = __decorate([ + decorate + ], C); return C; }()); -C.p = 1; -C = __decorate([ - decorate -], C); ; diff --git a/tests/baselines/reference/classMemberInitializerScoping.js b/tests/baselines/reference/classMemberInitializerScoping.js index 52bbaee8945..8f78cfb9ac6 100644 --- a/tests/baselines/reference/classMemberInitializerScoping.js +++ b/tests/baselines/reference/classMemberInitializerScoping.js @@ -27,9 +27,9 @@ var CCC = (function () { this.y = aaa; this.y = ''; // was: error, cannot assign string to number } + CCC.staticY = aaa; // This shouldnt be error return CCC; }()); -CCC.staticY = aaa; // This shouldnt be error // above is equivalent to this: var aaaa = 1; var CCCC = (function () { diff --git a/tests/baselines/reference/classMemberInitializerWithLamdaScoping.js b/tests/baselines/reference/classMemberInitializerWithLamdaScoping.js index c5b661831a2..752220a4cbc 100644 --- a/tests/baselines/reference/classMemberInitializerWithLamdaScoping.js +++ b/tests/baselines/reference/classMemberInitializerWithLamdaScoping.js @@ -40,12 +40,12 @@ var Test = (function () { console.log(field); // Using field here shouldnt be error }; } + Test.staticMessageHandler = function () { + var field = Test.field; + console.log(field); // Using field here shouldnt be error + }; return Test; }()); -Test.staticMessageHandler = function () { - var field = Test.field; - console.log(field); // Using field here shouldnt be error -}; var field1; var Test1 = (function () { function Test1(field1) { @@ -56,8 +56,8 @@ var Test1 = (function () { // it would resolve to private field1 and thats not what user intended here. }; } + Test1.staticMessageHandler = function () { + console.log(field1); // This shouldnt be error as its a static property + }; return Test1; }()); -Test1.staticMessageHandler = function () { - console.log(field1); // This shouldnt be error as its a static property -}; diff --git a/tests/baselines/reference/classWithPrivateProperty.js b/tests/baselines/reference/classWithPrivateProperty.js index c94f1d8ed80..6e75797523f 100644 --- a/tests/baselines/reference/classWithPrivateProperty.js +++ b/tests/baselines/reference/classWithPrivateProperty.js @@ -32,9 +32,9 @@ var C = (function () { } C.prototype.c = function () { return ''; }; C.f = function () { return ''; }; + C.g = function () { return ''; }; return C; }()); -C.g = function () { return ''; }; var c = new C(); var r1 = c.x; var r2 = c.a; diff --git a/tests/baselines/reference/classWithProtectedProperty.js b/tests/baselines/reference/classWithProtectedProperty.js index 2b12741d38f..2bc766cd99a 100644 --- a/tests/baselines/reference/classWithProtectedProperty.js +++ b/tests/baselines/reference/classWithProtectedProperty.js @@ -47,9 +47,9 @@ var C = (function () { } C.prototype.c = function () { return ''; }; C.f = function () { return ''; }; + C.g = function () { return ''; }; return C; }()); -C.g = function () { return ''; }; var D = (function (_super) { __extends(D, _super); function D() { diff --git a/tests/baselines/reference/classWithPublicProperty.js b/tests/baselines/reference/classWithPublicProperty.js index 47708b7aff3..054713264bd 100644 --- a/tests/baselines/reference/classWithPublicProperty.js +++ b/tests/baselines/reference/classWithPublicProperty.js @@ -30,9 +30,9 @@ var C = (function () { } C.prototype.c = function () { return ''; }; C.f = function () { return ''; }; + C.g = function () { return ''; }; return C; }()); -C.g = function () { return ''; }; // all of these are valid var c = new C(); var r1 = c.x; diff --git a/tests/baselines/reference/cloduleStaticMembers.js b/tests/baselines/reference/cloduleStaticMembers.js index b696a842f3b..d17a2b2497d 100644 --- a/tests/baselines/reference/cloduleStaticMembers.js +++ b/tests/baselines/reference/cloduleStaticMembers.js @@ -16,10 +16,10 @@ module Clod { var Clod = (function () { function Clod() { } + Clod.x = 10; + Clod.y = 10; return Clod; }()); -Clod.x = 10; -Clod.y = 10; (function (Clod) { var p = Clod.x; var q = x; diff --git a/tests/baselines/reference/commentOnDecoratedClassDeclaration.js b/tests/baselines/reference/commentOnDecoratedClassDeclaration.js index 44a7047a2ac..8e6cd7149cf 100644 --- a/tests/baselines/reference/commentOnDecoratedClassDeclaration.js +++ b/tests/baselines/reference/commentOnDecoratedClassDeclaration.js @@ -29,19 +29,19 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var Remote = (function () { function Remote() { } + Remote = __decorate([ + decorator("hello") + ], Remote); return Remote; }()); -Remote = __decorate([ - decorator("hello") -], Remote); /** * Floating Comment */ var AnotherRomote = (function () { function AnotherRomote() { } + AnotherRomote = __decorate([ + decorator("hi") + ], AnotherRomote); return AnotherRomote; }()); -AnotherRomote = __decorate([ - decorator("hi") -], AnotherRomote); diff --git a/tests/baselines/reference/commentsOnStaticMembers.js b/tests/baselines/reference/commentsOnStaticMembers.js index 94df4089880..896aced36e4 100644 --- a/tests/baselines/reference/commentsOnStaticMembers.js +++ b/tests/baselines/reference/commentsOnStaticMembers.js @@ -23,13 +23,13 @@ class test { var test = (function () { function test() { } + /** + * p1 comment appears in output + */ + test.p1 = ""; + /** + * p3 comment appears in output + */ + test.p3 = ""; return test; }()); -/** - * p1 comment appears in output - */ -test.p1 = ""; -/** - * p3 comment appears in output - */ -test.p3 = ""; diff --git a/tests/baselines/reference/commonJSImportAsPrimaryExpression.js b/tests/baselines/reference/commonJSImportAsPrimaryExpression.js index cd62c1583bc..d25c1410897 100644 --- a/tests/baselines/reference/commonJSImportAsPrimaryExpression.js +++ b/tests/baselines/reference/commonJSImportAsPrimaryExpression.js @@ -20,9 +20,9 @@ var C1 = (function () { function C1() { this.m1 = 42; } + C1.s1 = true; return C1; }()); -C1.s1 = true; exports.C1 = C1; //// [foo_1.js] "use strict"; diff --git a/tests/baselines/reference/commonJSImportNotAsPrimaryExpression.js b/tests/baselines/reference/commonJSImportNotAsPrimaryExpression.js index 5ac0e3fcc64..7aee50e1106 100644 --- a/tests/baselines/reference/commonJSImportNotAsPrimaryExpression.js +++ b/tests/baselines/reference/commonJSImportNotAsPrimaryExpression.js @@ -38,9 +38,9 @@ var C1 = (function () { function C1() { this.m1 = 42; } + C1.s1 = true; return C1; }()); -C1.s1 = true; exports.C1 = C1; var E1; (function (E1) { diff --git a/tests/baselines/reference/computedPropertyNames12_ES5.js b/tests/baselines/reference/computedPropertyNames12_ES5.js index 10427b5dc13..2aec8856286 100644 --- a/tests/baselines/reference/computedPropertyNames12_ES5.js +++ b/tests/baselines/reference/computedPropertyNames12_ES5.js @@ -26,6 +26,6 @@ var C = (function () { this[s + n] = 2; this["hello bye"] = 0; } + C["hello " + a + " bye"] = 0; return C; }()); -C["hello " + a + " bye"] = 0; diff --git a/tests/baselines/reference/constructableDecoratorOnClass01.js b/tests/baselines/reference/constructableDecoratorOnClass01.js index 858d67923af..a37f96b59d1 100644 --- a/tests/baselines/reference/constructableDecoratorOnClass01.js +++ b/tests/baselines/reference/constructableDecoratorOnClass01.js @@ -22,8 +22,8 @@ var CtorDtor = (function () { var C = (function () { function C() { } + C = __decorate([ + CtorDtor + ], C); return C; }()); -C = __decorate([ - CtorDtor -], C); diff --git a/tests/baselines/reference/declFilePrivateStatic.js b/tests/baselines/reference/declFilePrivateStatic.js index cb1b47735f3..409e2f21b42 100644 --- a/tests/baselines/reference/declFilePrivateStatic.js +++ b/tests/baselines/reference/declFilePrivateStatic.js @@ -39,10 +39,10 @@ var C = (function () { enumerable: true, configurable: true }); + C.x = 1; + C.y = 1; return C; }()); -C.x = 1; -C.y = 1; //// [declFilePrivateStatic.d.ts] diff --git a/tests/baselines/reference/decoratorCallGeneric.js b/tests/baselines/reference/decoratorCallGeneric.js index a1d470b7063..acc9c48297d 100644 --- a/tests/baselines/reference/decoratorCallGeneric.js +++ b/tests/baselines/reference/decoratorCallGeneric.js @@ -24,8 +24,8 @@ var C = (function () { function C() { } C.m = function () { }; + C = __decorate([ + dec + ], C); return C; }()); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/decoratorChecksFunctionBodies.js b/tests/baselines/reference/decoratorChecksFunctionBodies.js index 20a58980e44..562169078af 100644 --- a/tests/baselines/reference/decoratorChecksFunctionBodies.js +++ b/tests/baselines/reference/decoratorChecksFunctionBodies.js @@ -29,12 +29,12 @@ var A = (function () { } A.prototype.m = function () { }; + __decorate([ + (function (x, p) { + var a = 3; + func(a); + return x; + }) + ], A.prototype, "m", null); return A; }()); -__decorate([ - (function (x, p) { - var a = 3; - func(a); - return x; - }) -], A.prototype, "m", null); diff --git a/tests/baselines/reference/decoratorInstantiateModulesInFunctionBodies.js b/tests/baselines/reference/decoratorInstantiateModulesInFunctionBodies.js index 08184bb7e6c..fccd0ec95d3 100644 --- a/tests/baselines/reference/decoratorInstantiateModulesInFunctionBodies.js +++ b/tests/baselines/reference/decoratorInstantiateModulesInFunctionBodies.js @@ -46,8 +46,8 @@ var Wat = (function () { Wat.whatever = function () { // ... }; + __decorate([ + filter(function () { return a_1.test == 'abc'; }) + ], Wat, "whatever", null); return Wat; }()); -__decorate([ - filter(function () { return a_1.test == 'abc'; }) -], Wat, "whatever", null); diff --git a/tests/baselines/reference/decoratorMetadata.js b/tests/baselines/reference/decoratorMetadata.js index 9998ae3d08a..93453ac4cf3 100644 --- a/tests/baselines/reference/decoratorMetadata.js +++ b/tests/baselines/reference/decoratorMetadata.js @@ -46,15 +46,15 @@ var MyComponent = (function () { } MyComponent.prototype.method = function (x) { }; + __decorate([ + decorator, + __metadata("design:type", Function), + __metadata("design:paramtypes", [Object]), + __metadata("design:returntype", void 0) + ], MyComponent.prototype, "method", null); + MyComponent = __decorate([ + decorator, + __metadata("design:paramtypes", [service_1.default]) + ], MyComponent); return MyComponent; }()); -__decorate([ - decorator, - __metadata("design:type", Function), - __metadata("design:paramtypes", [Object]), - __metadata("design:returntype", void 0) -], MyComponent.prototype, "method", null); -MyComponent = __decorate([ - decorator, - __metadata("design:paramtypes", [service_1.default]) -], MyComponent); diff --git a/tests/baselines/reference/decoratorMetadataForMethodWithNoReturnTypeAnnotation01.js b/tests/baselines/reference/decoratorMetadataForMethodWithNoReturnTypeAnnotation01.js index 9647165b650..9e8b4d5278e 100644 --- a/tests/baselines/reference/decoratorMetadataForMethodWithNoReturnTypeAnnotation01.js +++ b/tests/baselines/reference/decoratorMetadataForMethodWithNoReturnTypeAnnotation01.js @@ -19,11 +19,11 @@ var MyClass = (function () { } MyClass.prototype.doSomething = function () { }; + __decorate([ + decorator, + __metadata("design:type", Function), + __metadata("design:paramtypes", []), + __metadata("design:returntype", void 0) + ], MyClass.prototype, "doSomething", null); return MyClass; }()); -__decorate([ - decorator, - __metadata("design:type", Function), - __metadata("design:paramtypes", []), - __metadata("design:returntype", void 0) -], MyClass.prototype, "doSomething", null); diff --git a/tests/baselines/reference/decoratorMetadataOnInferredType.js b/tests/baselines/reference/decoratorMetadataOnInferredType.js index e7bd55ada6f..4c532327d25 100644 --- a/tests/baselines/reference/decoratorMetadataOnInferredType.js +++ b/tests/baselines/reference/decoratorMetadataOnInferredType.js @@ -31,10 +31,10 @@ var B = (function () { function B() { this.x = new A(); } + __decorate([ + decorator, + __metadata("design:type", Object) + ], B.prototype, "x", void 0); return B; }()); -__decorate([ - decorator, - __metadata("design:type", Object) -], B.prototype, "x", void 0); exports.B = B; diff --git a/tests/baselines/reference/decoratorMetadataRestParameterWithImportedType.js b/tests/baselines/reference/decoratorMetadataRestParameterWithImportedType.js index 404bc9a1d59..f85bb476721 100644 --- a/tests/baselines/reference/decoratorMetadataRestParameterWithImportedType.js +++ b/tests/baselines/reference/decoratorMetadataRestParameterWithImportedType.js @@ -100,16 +100,16 @@ var ClassA = (function () { args[_i] = arguments[_i]; } }; + __decorate([ + annotation1(), + __metadata("design:type", Function), + __metadata("design:paramtypes", [aux1_1.SomeClass1]), + __metadata("design:returntype", void 0) + ], ClassA.prototype, "foo", null); + ClassA = __decorate([ + annotation(), + __metadata("design:paramtypes", [aux_1.SomeClass]) + ], ClassA); return ClassA; }()); -__decorate([ - annotation1(), - __metadata("design:type", Function), - __metadata("design:paramtypes", [aux1_1.SomeClass1]), - __metadata("design:returntype", void 0) -], ClassA.prototype, "foo", null); -ClassA = __decorate([ - annotation(), - __metadata("design:paramtypes", [aux_1.SomeClass]) -], ClassA); exports.ClassA = ClassA; diff --git a/tests/baselines/reference/decoratorMetadataWithConstructorType.js b/tests/baselines/reference/decoratorMetadataWithConstructorType.js index 95c19178345..6eff4fdc282 100644 --- a/tests/baselines/reference/decoratorMetadataWithConstructorType.js +++ b/tests/baselines/reference/decoratorMetadataWithConstructorType.js @@ -31,10 +31,10 @@ var B = (function () { function B() { this.x = new A(); } + __decorate([ + decorator, + __metadata("design:type", A) + ], B.prototype, "x", void 0); return B; }()); -__decorate([ - decorator, - __metadata("design:type", A) -], B.prototype, "x", void 0); exports.B = B; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision.js index b0e23a78971..f59e7f9ec13 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [db_1.db]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [db_1.db]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision2.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision2.js index f03190cff0c..b3a5cded571 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision2.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision2.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [db_1.db]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [db_1.db]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision3.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision3.js index c1eca081527..a3c170b24e6 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision3.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision3.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [db.db]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [db.db]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision4.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision4.js index 7d78cf7adbe..d6ed8bde3ec 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision4.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision4.js @@ -46,11 +46,11 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [typeof (_a = (typeof db_1.default !== "undefined" && db_1.default).db) === "function" && _a || Object]) + ], MyClass); return MyClass; + var _a; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [typeof (_a = (typeof db_1.default !== "undefined" && db_1.default).db) === "function" && _a || Object]) -], MyClass); exports.MyClass = MyClass; -var _a; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision5.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision5.js index 3f7069902ce..a1cc10b7d3d 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision5.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision5.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [db_1.default]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [db_1.default]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision6.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision6.js index 66eb30dc710..572787b6f20 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision6.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision6.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [db_1.default]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [db_1.default]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision7.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision7.js index 1dd09c3a177..6a45f5230bd 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision7.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision7.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [Object]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [Object]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision8.js b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision8.js index 830e6bc80ee..6efdc7f26db 100644 --- a/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision8.js +++ b/tests/baselines/reference/decoratorMetadataWithImportDeclarationNameCollision8.js @@ -46,10 +46,10 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [database.db]) + ], MyClass); return MyClass; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [database.db]) -], MyClass); exports.MyClass = MyClass; diff --git a/tests/baselines/reference/decoratorOnClass1.js b/tests/baselines/reference/decoratorOnClass1.js index 5cff4c2649c..7ea46b4698f 100644 --- a/tests/baselines/reference/decoratorOnClass1.js +++ b/tests/baselines/reference/decoratorOnClass1.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + C = __decorate([ + dec + ], C); return C; }()); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/decoratorOnClass2.js b/tests/baselines/reference/decoratorOnClass2.js index 77020e7cb77..84098a17870 100644 --- a/tests/baselines/reference/decoratorOnClass2.js +++ b/tests/baselines/reference/decoratorOnClass2.js @@ -17,9 +17,9 @@ Object.defineProperty(exports, "__esModule", { value: true }); var C = (function () { function C() { } + C = __decorate([ + dec + ], C); return C; }()); -C = __decorate([ - dec -], C); exports.C = C; diff --git a/tests/baselines/reference/decoratorOnClass3.js b/tests/baselines/reference/decoratorOnClass3.js index fd09a6d8de5..5a3601fc1f3 100644 --- a/tests/baselines/reference/decoratorOnClass3.js +++ b/tests/baselines/reference/decoratorOnClass3.js @@ -16,8 +16,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + C = __decorate([ + dec + ], C); return C; }()); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/decoratorOnClass4.js b/tests/baselines/reference/decoratorOnClass4.js index daf19e20327..adbe30db662 100644 --- a/tests/baselines/reference/decoratorOnClass4.js +++ b/tests/baselines/reference/decoratorOnClass4.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + C = __decorate([ + dec() + ], C); return C; }()); -C = __decorate([ - dec() -], C); diff --git a/tests/baselines/reference/decoratorOnClass5.js b/tests/baselines/reference/decoratorOnClass5.js index 70fc5515140..6741b26373b 100644 --- a/tests/baselines/reference/decoratorOnClass5.js +++ b/tests/baselines/reference/decoratorOnClass5.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + C = __decorate([ + dec() + ], C); return C; }()); -C = __decorate([ - dec() -], C); diff --git a/tests/baselines/reference/decoratorOnClass8.js b/tests/baselines/reference/decoratorOnClass8.js index ae50ab75ab8..e5cd8812ea7 100644 --- a/tests/baselines/reference/decoratorOnClass8.js +++ b/tests/baselines/reference/decoratorOnClass8.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + C = __decorate([ + dec() + ], C); return C; }()); -C = __decorate([ - dec() -], C); diff --git a/tests/baselines/reference/decoratorOnClassAccessor1.js b/tests/baselines/reference/decoratorOnClassAccessor1.js index 27966350fae..cf989705b79 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor1.js +++ b/tests/baselines/reference/decoratorOnClassAccessor1.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor2.js b/tests/baselines/reference/decoratorOnClassAccessor2.js index 57cb3b50461..9e9455b4380 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor2.js +++ b/tests/baselines/reference/decoratorOnClassAccessor2.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor3.js b/tests/baselines/reference/decoratorOnClassAccessor3.js index c02f984e70a..8a27914e0c8 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor3.js +++ b/tests/baselines/reference/decoratorOnClassAccessor3.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor4.js b/tests/baselines/reference/decoratorOnClassAccessor4.js index 0e0af58f526..85b35e95cef 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor4.js +++ b/tests/baselines/reference/decoratorOnClassAccessor4.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor5.js b/tests/baselines/reference/decoratorOnClassAccessor5.js index c7d5d109cc0..12ec7a08adc 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor5.js +++ b/tests/baselines/reference/decoratorOnClassAccessor5.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor6.js b/tests/baselines/reference/decoratorOnClassAccessor6.js index 8ac40e72299..d5477deb5af 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor6.js +++ b/tests/baselines/reference/decoratorOnClassAccessor6.js @@ -20,8 +20,8 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec + ], C.prototype, "accessor", null); return C; }()); -__decorate([ - dec -], C.prototype, "accessor", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor7.js b/tests/baselines/reference/decoratorOnClassAccessor7.js index 5ae0c29c14b..26f0ce5c215 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor7.js +++ b/tests/baselines/reference/decoratorOnClassAccessor7.js @@ -48,11 +48,11 @@ var A = (function () { enumerable: true, configurable: true }); + __decorate([ + dec1 + ], A.prototype, "x", null); return A; }()); -__decorate([ - dec1 -], A.prototype, "x", null); var B = (function () { function B() { } @@ -62,11 +62,11 @@ var B = (function () { enumerable: true, configurable: true }); + __decorate([ + dec2 + ], B.prototype, "x", null); return B; }()); -__decorate([ - dec2 -], B.prototype, "x", null); var C = (function () { function C() { } @@ -76,11 +76,11 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec1 + ], C.prototype, "x", null); return C; }()); -__decorate([ - dec1 -], C.prototype, "x", null); var D = (function () { function D() { } @@ -90,11 +90,11 @@ var D = (function () { enumerable: true, configurable: true }); + __decorate([ + dec2 + ], D.prototype, "x", null); return D; }()); -__decorate([ - dec2 -], D.prototype, "x", null); var E = (function () { function E() { } @@ -104,11 +104,11 @@ var E = (function () { enumerable: true, configurable: true }); + __decorate([ + dec1 + ], E.prototype, "x", null); return E; }()); -__decorate([ - dec1 -], E.prototype, "x", null); var F = (function () { function F() { } @@ -118,8 +118,8 @@ var F = (function () { enumerable: true, configurable: true }); + __decorate([ + dec1 + ], F.prototype, "x", null); return F; }()); -__decorate([ - dec1 -], F.prototype, "x", null); diff --git a/tests/baselines/reference/decoratorOnClassAccessor8.js b/tests/baselines/reference/decoratorOnClassAccessor8.js index 7347e630eab..f121d148623 100644 --- a/tests/baselines/reference/decoratorOnClassAccessor8.js +++ b/tests/baselines/reference/decoratorOnClassAccessor8.js @@ -48,13 +48,13 @@ var A = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Object), + __metadata("design:paramtypes", [Number]) + ], A.prototype, "x", null); return A; }()); -__decorate([ - dec, - __metadata("design:type", Object), - __metadata("design:paramtypes", [Number]) -], A.prototype, "x", null); var B = (function () { function B() { } @@ -64,13 +64,13 @@ var B = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Number), + __metadata("design:paramtypes", [Number]) + ], B.prototype, "x", null); return B; }()); -__decorate([ - dec, - __metadata("design:type", Number), - __metadata("design:paramtypes", [Number]) -], B.prototype, "x", null); var C = (function () { function C() { } @@ -80,13 +80,13 @@ var C = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Number), + __metadata("design:paramtypes", [Number]) + ], C.prototype, "x", null); return C; }()); -__decorate([ - dec, - __metadata("design:type", Number), - __metadata("design:paramtypes", [Number]) -], C.prototype, "x", null); var D = (function () { function D() { } @@ -96,13 +96,13 @@ var D = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Object), + __metadata("design:paramtypes", [Number]) + ], D.prototype, "x", null); return D; }()); -__decorate([ - dec, - __metadata("design:type", Object), - __metadata("design:paramtypes", [Number]) -], D.prototype, "x", null); var E = (function () { function E() { } @@ -111,13 +111,13 @@ var E = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Object), + __metadata("design:paramtypes", []) + ], E.prototype, "x", null); return E; }()); -__decorate([ - dec, - __metadata("design:type", Object), - __metadata("design:paramtypes", []) -], E.prototype, "x", null); var F = (function () { function F() { } @@ -126,10 +126,10 @@ var F = (function () { enumerable: true, configurable: true }); + __decorate([ + dec, + __metadata("design:type", Number), + __metadata("design:paramtypes", [Number]) + ], F.prototype, "x", null); return F; }()); -__decorate([ - dec, - __metadata("design:type", Number), - __metadata("design:paramtypes", [Number]) -], F.prototype, "x", null); diff --git a/tests/baselines/reference/decoratorOnClassConstructor2.js b/tests/baselines/reference/decoratorOnClassConstructor2.js index 999ffbc5e60..2e444b62e80 100644 --- a/tests/baselines/reference/decoratorOnClassConstructor2.js +++ b/tests/baselines/reference/decoratorOnClassConstructor2.js @@ -53,9 +53,9 @@ var C = (function (_super) { function C(prop) { return _super.call(this) || this; } + C = __decorate([ + __param(0, _0_ts_2.foo) + ], C); return C; }(_0_ts_1.base)); -C = __decorate([ - __param(0, _0_ts_2.foo) -], C); exports.C = C; diff --git a/tests/baselines/reference/decoratorOnClassConstructor3.js b/tests/baselines/reference/decoratorOnClassConstructor3.js index 98edaebe920..7d9573217c4 100644 --- a/tests/baselines/reference/decoratorOnClassConstructor3.js +++ b/tests/baselines/reference/decoratorOnClassConstructor3.js @@ -56,9 +56,9 @@ var C = (function (_super) { function C(prop) { return _super.call(this) || this; } + C = __decorate([ + __param(0, _0_2.foo) + ], C); return C; }(_0_1.base)); -C = __decorate([ - __param(0, _0_2.foo) -], C); exports.C = C; diff --git a/tests/baselines/reference/decoratorOnClassConstructor4.js b/tests/baselines/reference/decoratorOnClassConstructor4.js index 75286943417..62fc93cbaa0 100644 --- a/tests/baselines/reference/decoratorOnClassConstructor4.js +++ b/tests/baselines/reference/decoratorOnClassConstructor4.js @@ -37,27 +37,27 @@ var __metadata = (this && this.__metadata) || function (k, v) { var A = (function () { function A() { } + A = __decorate([ + dec + ], A); return A; }()); -A = __decorate([ - dec -], A); var B = (function () { function B(x) { } + B = __decorate([ + dec, + __metadata("design:paramtypes", [Number]) + ], B); return B; }()); -B = __decorate([ - dec, - __metadata("design:paramtypes", [Number]) -], B); var C = (function (_super) { __extends(C, _super); function C() { return _super !== null && _super.apply(this, arguments) || this; } + C = __decorate([ + dec + ], C); return C; }(A)); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/decoratorOnClassConstructorParameter1.js b/tests/baselines/reference/decoratorOnClassConstructorParameter1.js index 176e2309ae0..fe04f569e30 100644 --- a/tests/baselines/reference/decoratorOnClassConstructorParameter1.js +++ b/tests/baselines/reference/decoratorOnClassConstructorParameter1.js @@ -18,8 +18,8 @@ var __param = (this && this.__param) || function (paramIndex, decorator) { var C = (function () { function C(p) { } + C = __decorate([ + __param(0, dec) + ], C); return C; }()); -C = __decorate([ - __param(0, dec) -], C); diff --git a/tests/baselines/reference/decoratorOnClassConstructorParameter4.js b/tests/baselines/reference/decoratorOnClassConstructorParameter4.js index e14f0358808..8d02bd467d6 100644 --- a/tests/baselines/reference/decoratorOnClassConstructorParameter4.js +++ b/tests/baselines/reference/decoratorOnClassConstructorParameter4.js @@ -18,8 +18,8 @@ var __param = (this && this.__param) || function (paramIndex, decorator) { var C = (function () { function C(public, p) { } + C = __decorate([ + __param(1, dec) + ], C); return C; }()); -C = __decorate([ - __param(1, dec) -], C); diff --git a/tests/baselines/reference/decoratorOnClassMethod1.js b/tests/baselines/reference/decoratorOnClassMethod1.js index b93d7f88771..ef029b84543 100644 --- a/tests/baselines/reference/decoratorOnClassMethod1.js +++ b/tests/baselines/reference/decoratorOnClassMethod1.js @@ -16,8 +16,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethod10.js b/tests/baselines/reference/decoratorOnClassMethod10.js index bfa57f0aeb7..f90251d6196 100644 --- a/tests/baselines/reference/decoratorOnClassMethod10.js +++ b/tests/baselines/reference/decoratorOnClassMethod10.js @@ -16,8 +16,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethod11.js b/tests/baselines/reference/decoratorOnClassMethod11.js index c703459b88d..f1589a39286 100644 --- a/tests/baselines/reference/decoratorOnClassMethod11.js +++ b/tests/baselines/reference/decoratorOnClassMethod11.js @@ -22,9 +22,9 @@ var M; } C.prototype.decorator = function (target, key) { }; C.prototype.method = function () { }; + __decorate([ + this.decorator + ], C.prototype, "method", null); return C; }()); - __decorate([ - this.decorator - ], C.prototype, "method", null); })(M || (M = {})); diff --git a/tests/baselines/reference/decoratorOnClassMethod12.js b/tests/baselines/reference/decoratorOnClassMethod12.js index c9ff30307f0..089f5961d9c 100644 --- a/tests/baselines/reference/decoratorOnClassMethod12.js +++ b/tests/baselines/reference/decoratorOnClassMethod12.js @@ -40,9 +40,9 @@ var M; return _super !== null && _super.apply(this, arguments) || this; } C.prototype.method = function () { }; + __decorate([ + _super.decorator + ], C.prototype, "method", null); return C; }(S)); - __decorate([ - _super.decorator - ], C.prototype, "method", null); })(M || (M = {})); diff --git a/tests/baselines/reference/decoratorOnClassMethod2.js b/tests/baselines/reference/decoratorOnClassMethod2.js index 98ad8ad43ad..5db2922ed71 100644 --- a/tests/baselines/reference/decoratorOnClassMethod2.js +++ b/tests/baselines/reference/decoratorOnClassMethod2.js @@ -16,8 +16,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethod3.js b/tests/baselines/reference/decoratorOnClassMethod3.js index 4a5943681d4..30f527368f2 100644 --- a/tests/baselines/reference/decoratorOnClassMethod3.js +++ b/tests/baselines/reference/decoratorOnClassMethod3.js @@ -16,8 +16,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethod8.js b/tests/baselines/reference/decoratorOnClassMethod8.js index c1ad826cab0..bf8c06d9b90 100644 --- a/tests/baselines/reference/decoratorOnClassMethod8.js +++ b/tests/baselines/reference/decoratorOnClassMethod8.js @@ -16,8 +16,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethodOverload2.js b/tests/baselines/reference/decoratorOnClassMethodOverload2.js index db077dd7b51..eafa5da7110 100644 --- a/tests/baselines/reference/decoratorOnClassMethodOverload2.js +++ b/tests/baselines/reference/decoratorOnClassMethodOverload2.js @@ -18,8 +18,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassMethodParameter1.js b/tests/baselines/reference/decoratorOnClassMethodParameter1.js index d5d8599d7a8..efb1e4abff2 100644 --- a/tests/baselines/reference/decoratorOnClassMethodParameter1.js +++ b/tests/baselines/reference/decoratorOnClassMethodParameter1.js @@ -19,8 +19,8 @@ var C = (function () { function C() { } C.prototype.method = function (p) { }; + __decorate([ + __param(0, dec) + ], C.prototype, "method", null); return C; }()); -__decorate([ - __param(0, dec) -], C.prototype, "method", null); diff --git a/tests/baselines/reference/decoratorOnClassProperty1.js b/tests/baselines/reference/decoratorOnClassProperty1.js index 6547e0bdb18..65a399332f1 100644 --- a/tests/baselines/reference/decoratorOnClassProperty1.js +++ b/tests/baselines/reference/decoratorOnClassProperty1.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty10.js b/tests/baselines/reference/decoratorOnClassProperty10.js index 174f26a315a..9df40eaf83a 100644 --- a/tests/baselines/reference/decoratorOnClassProperty10.js +++ b/tests/baselines/reference/decoratorOnClassProperty10.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec() + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec() -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty11.js b/tests/baselines/reference/decoratorOnClassProperty11.js index c901637402d..8b771caf8b5 100644 --- a/tests/baselines/reference/decoratorOnClassProperty11.js +++ b/tests/baselines/reference/decoratorOnClassProperty11.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty2.js b/tests/baselines/reference/decoratorOnClassProperty2.js index ceaf43caa59..3ab2b515e3c 100644 --- a/tests/baselines/reference/decoratorOnClassProperty2.js +++ b/tests/baselines/reference/decoratorOnClassProperty2.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty3.js b/tests/baselines/reference/decoratorOnClassProperty3.js index 8436be93968..9c0d3f90e42 100644 --- a/tests/baselines/reference/decoratorOnClassProperty3.js +++ b/tests/baselines/reference/decoratorOnClassProperty3.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty6.js b/tests/baselines/reference/decoratorOnClassProperty6.js index c7f5490c648..823a652af24 100644 --- a/tests/baselines/reference/decoratorOnClassProperty6.js +++ b/tests/baselines/reference/decoratorOnClassProperty6.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorOnClassProperty7.js b/tests/baselines/reference/decoratorOnClassProperty7.js index 828d548ff6b..134f35022e0 100644 --- a/tests/baselines/reference/decoratorOnClassProperty7.js +++ b/tests/baselines/reference/decoratorOnClassProperty7.js @@ -15,8 +15,8 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, var C = (function () { function C() { } + __decorate([ + dec + ], C.prototype, "prop", void 0); return C; }()); -__decorate([ - dec -], C.prototype, "prop", void 0); diff --git a/tests/baselines/reference/decoratorWithUnderscoreMethod.js b/tests/baselines/reference/decoratorWithUnderscoreMethod.js index 9ac2a88aa51..ace73ccf595 100644 --- a/tests/baselines/reference/decoratorWithUnderscoreMethod.js +++ b/tests/baselines/reference/decoratorWithUnderscoreMethod.js @@ -29,8 +29,8 @@ var A = (function () { A.prototype.__foo = function (bar) { // do something with bar }; + __decorate([ + dec() + ], A.prototype, "__foo"); return A; }()); -__decorate([ - dec() -], A.prototype, "__foo"); diff --git a/tests/baselines/reference/derivedClassSuperCallsInNonConstructorMembers.js b/tests/baselines/reference/derivedClassSuperCallsInNonConstructorMembers.js index 8703215a631..3ca0d13e671 100644 --- a/tests/baselines/reference/derivedClassSuperCallsInNonConstructorMembers.js +++ b/tests/baselines/reference/derivedClassSuperCallsInNonConstructorMembers.js @@ -83,6 +83,6 @@ var Derived = (function (_super) { enumerable: true, configurable: true }); + Derived.a = _this = _super.call(this) || this; return Derived; }(Base)); -Derived.a = _this = _super.call(this) || this; diff --git a/tests/baselines/reference/emitDecoratorMetadata_object.js b/tests/baselines/reference/emitDecoratorMetadata_object.js index a8c8c360dfc..ff4a65710a7 100644 --- a/tests/baselines/reference/emitDecoratorMetadata_object.js +++ b/tests/baselines/reference/emitDecoratorMetadata_object.js @@ -24,15 +24,15 @@ var A = (function () { function A(hi) { } A.prototype.method = function (there) { }; + __decorate([ + MyMethodDecorator, + __metadata("design:type", Function), + __metadata("design:paramtypes", [Object]), + __metadata("design:returntype", void 0) + ], A.prototype, "method", null); + A = __decorate([ + MyClassDecorator, + __metadata("design:paramtypes", [Object]) + ], A); return A; }()); -__decorate([ - MyMethodDecorator, - __metadata("design:type", Function), - __metadata("design:paramtypes", [Object]), - __metadata("design:returntype", void 0) -], A.prototype, "method", null); -A = __decorate([ - MyClassDecorator, - __metadata("design:paramtypes", [Object]) -], A); diff --git a/tests/baselines/reference/emitDecoratorMetadata_restArgs.js b/tests/baselines/reference/emitDecoratorMetadata_restArgs.js index 862a1baa025..3f1ffd54bce 100644 --- a/tests/baselines/reference/emitDecoratorMetadata_restArgs.js +++ b/tests/baselines/reference/emitDecoratorMetadata_restArgs.js @@ -40,18 +40,18 @@ var A = (function () { args[_i] = arguments[_i]; } }; + __decorate([ + MyMethodDecorator, + __metadata("design:type", Function), + __metadata("design:paramtypes", [Object]), + __metadata("design:returntype", void 0) + ], A.prototype, "method", null); + A = __decorate([ + MyClassDecorator, + __metadata("design:paramtypes", [Object]) + ], A); return A; }()); -__decorate([ - MyMethodDecorator, - __metadata("design:type", Function), - __metadata("design:paramtypes", [Object]), - __metadata("design:returntype", void 0) -], A.prototype, "method", null); -A = __decorate([ - MyClassDecorator, - __metadata("design:paramtypes", [Object]) -], A); var B = (function () { function B() { var args = []; @@ -65,15 +65,15 @@ var B = (function () { args[_i] = arguments[_i]; } }; + __decorate([ + MyMethodDecorator, + __metadata("design:type", Function), + __metadata("design:paramtypes", [String]), + __metadata("design:returntype", void 0) + ], B.prototype, "method", null); + B = __decorate([ + MyClassDecorator, + __metadata("design:paramtypes", [Number]) + ], B); return B; }()); -__decorate([ - MyMethodDecorator, - __metadata("design:type", Function), - __metadata("design:paramtypes", [String]), - __metadata("design:returntype", void 0) -], B.prototype, "method", null); -B = __decorate([ - MyClassDecorator, - __metadata("design:paramtypes", [Number]) -], B); diff --git a/tests/baselines/reference/errorSuperCalls.js b/tests/baselines/reference/errorSuperCalls.js index ebe9de27f42..db4f0ac1798 100644 --- a/tests/baselines/reference/errorSuperCalls.js +++ b/tests/baselines/reference/errorSuperCalls.js @@ -124,10 +124,10 @@ var NoBase = (function () { enumerable: true, configurable: true }); + //super call in static class member initializer with no base type + NoBase.k = _this = _super.call(this) || this; return NoBase; }()); -//super call in static class member initializer with no base type -NoBase.k = _this = _super.call(this) || this; var Base = (function () { function Base() { } diff --git a/tests/baselines/reference/errorSuperPropertyAccess.js b/tests/baselines/reference/errorSuperPropertyAccess.js index b33755e245a..3163007e742 100644 --- a/tests/baselines/reference/errorSuperPropertyAccess.js +++ b/tests/baselines/reference/errorSuperPropertyAccess.js @@ -180,10 +180,10 @@ var SomeBase = (function () { SomeBase.prototype.publicFunc = function () { }; SomeBase.privateStaticFunc = function () { }; SomeBase.publicStaticFunc = function () { }; + SomeBase.privateStaticMember = 0; + SomeBase.publicStaticMember = 0; return SomeBase; }()); -SomeBase.privateStaticMember = 0; -SomeBase.publicStaticMember = 0; //super.publicInstanceMemberNotFunction in constructor of derived class //super.publicInstanceMemberNotFunction in instance member function of derived class //super.publicInstanceMemberNotFunction in instance member accessor(get and set) of derived class diff --git a/tests/baselines/reference/es3defaultAliasIsQuoted.js b/tests/baselines/reference/es3defaultAliasIsQuoted.js index ea12fc7a3d6..ccc2085f97a 100644 --- a/tests/baselines/reference/es3defaultAliasIsQuoted.js +++ b/tests/baselines/reference/es3defaultAliasIsQuoted.js @@ -19,9 +19,9 @@ exports.__esModule = true; var Foo = (function () { function Foo() { } + Foo.CONSTANT = "Foo"; return Foo; }()); -Foo.CONSTANT = "Foo"; exports.Foo = Foo; function assert(value) { if (!value) diff --git a/tests/baselines/reference/es6ClassTest.js b/tests/baselines/reference/es6ClassTest.js index 9d66d2d8dc8..d727ab49a34 100644 --- a/tests/baselines/reference/es6ClassTest.js +++ b/tests/baselines/reference/es6ClassTest.js @@ -119,9 +119,9 @@ var Foo = (function (_super) { } Foo.prototype.bar = function () { return 0; }; Foo.prototype.boo = function (x) { return x; }; + Foo.statVal = 0; return Foo; }(Bar)); -Foo.statVal = 0; var f = new Foo(); //class GetSetMonster { // // attack(target) { diff --git a/tests/baselines/reference/es6ClassTest2.js b/tests/baselines/reference/es6ClassTest2.js index e86d04bccd0..216a05ac2eb 100644 --- a/tests/baselines/reference/es6ClassTest2.js +++ b/tests/baselines/reference/es6ClassTest2.js @@ -288,9 +288,9 @@ var Statics = (function () { Statics.baz = function () { return ""; }; + Statics.foo = 1; return Statics; }()); -Statics.foo = 1; var stat = new Statics(); var ImplementsInterface = (function () { function ImplementsInterface() { diff --git a/tests/baselines/reference/es6modulekindWithES5Target.js b/tests/baselines/reference/es6modulekindWithES5Target.js index 8778d178786..b813bc01992 100644 --- a/tests/baselines/reference/es6modulekindWithES5Target.js +++ b/tests/baselines/reference/es6modulekindWithES5Target.js @@ -31,22 +31,22 @@ var C = (function () { this.p = 1; } C.prototype.method = function () { }; + C.s = 0; return C; }()); export { C }; -C.s = 0; export { C as C2 }; var D = (function () { function D() { this.p = 1; } D.prototype.method = function () { }; + D.s = 0; + D = __decorate([ + foo + ], D); return D; }()); -D.s = 0; -D = __decorate([ - foo -], D); export { D }; export { D as D2 }; var E = (function () { diff --git a/tests/baselines/reference/es6modulekindWithES5Target11.js b/tests/baselines/reference/es6modulekindWithES5Target11.js index ed3d44cb538..e958b0ca1c6 100644 --- a/tests/baselines/reference/es6modulekindWithES5Target11.js +++ b/tests/baselines/reference/es6modulekindWithES5Target11.js @@ -15,17 +15,17 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key, else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; return c > 3 && r && Object.defineProperty(target, key, r), r; }; -var C = C_1 = (function () { - function C() { +var C = (function () { + var C = C_1 = function C() { this.p = 1; - } + }; C.x = function () { return C_1.y; }; C.prototype.method = function () { }; + C.y = 1; + C = C_1 = __decorate([ + foo + ], C); return C; + var C_1; }()); -C.y = 1; -C = C_1 = __decorate([ - foo -], C); export default C; -var C_1; diff --git a/tests/baselines/reference/es6modulekindWithES5Target2.js b/tests/baselines/reference/es6modulekindWithES5Target2.js index 8b2f6dd3c53..a67bba11e23 100644 --- a/tests/baselines/reference/es6modulekindWithES5Target2.js +++ b/tests/baselines/reference/es6modulekindWithES5Target2.js @@ -12,7 +12,7 @@ var C = (function () { this.p = 1; } C.prototype.method = function () { }; + C.s = 0; return C; }()); export default C; -C.s = 0; diff --git a/tests/baselines/reference/es6modulekindWithES5Target3.js b/tests/baselines/reference/es6modulekindWithES5Target3.js index 87dd0409097..2a9778691a6 100644 --- a/tests/baselines/reference/es6modulekindWithES5Target3.js +++ b/tests/baselines/reference/es6modulekindWithES5Target3.js @@ -19,10 +19,10 @@ var D = (function () { this.p = 1; } D.prototype.method = function () { }; + D.s = 0; + D = __decorate([ + foo + ], D); return D; }()); -D.s = 0; -D = __decorate([ - foo -], D); export default D; diff --git a/tests/baselines/reference/extendFromAny.js b/tests/baselines/reference/extendFromAny.js index f2a7f945cc9..33610fd8b1f 100644 --- a/tests/baselines/reference/extendFromAny.js +++ b/tests/baselines/reference/extendFromAny.js @@ -30,9 +30,9 @@ var C = (function (_super) { _this.known = 1; return _this; } + C.sknown = 2; return C; }(Base)); -C.sknown = 2; var c = new C(); c.known.length; // error, 'known' has no 'length' property C.sknown.length; // error, 'sknown' has no 'length' property diff --git a/tests/baselines/reference/forwardRefInClassProperties.js b/tests/baselines/reference/forwardRefInClassProperties.js index 1dc455729ab..424d950055d 100644 --- a/tests/baselines/reference/forwardRefInClassProperties.js +++ b/tests/baselines/reference/forwardRefInClassProperties.js @@ -25,7 +25,7 @@ var Test = (function () { var a = b; // Block-scoped variable 'b' used before its declaration var b = 3; }; + Test._B = Test._A; // undefined, no error/warning + Test._A = 3; return Test; }()); -Test._B = Test._A; // undefined, no error/warning -Test._A = 3; diff --git a/tests/baselines/reference/generatedContextualTyping.js b/tests/baselines/reference/generatedContextualTyping.js index 8b0889f28ae..a5d5a418327 100644 --- a/tests/baselines/reference/generatedContextualTyping.js +++ b/tests/baselines/reference/generatedContextualTyping.js @@ -616,219 +616,219 @@ var x48 = (function () { var x49 = (function () { function x49() { } + x49.member = function () { return [d1, d2]; }; return x49; }()); -x49.member = function () { return [d1, d2]; }; var x50 = (function () { function x50() { } + x50.member = function () { return [d1, d2]; }; return x50; }()); -x50.member = function () { return [d1, d2]; }; var x51 = (function () { function x51() { } + x51.member = function named() { return [d1, d2]; }; return x51; }()); -x51.member = function named() { return [d1, d2]; }; var x52 = (function () { function x52() { } + x52.member = function () { return [d1, d2]; }; return x52; }()); -x52.member = function () { return [d1, d2]; }; var x53 = (function () { function x53() { } + x53.member = function () { return [d1, d2]; }; return x53; }()); -x53.member = function () { return [d1, d2]; }; var x54 = (function () { function x54() { } + x54.member = function named() { return [d1, d2]; }; return x54; }()); -x54.member = function named() { return [d1, d2]; }; var x55 = (function () { function x55() { } + x55.member = [d1, d2]; return x55; }()); -x55.member = [d1, d2]; var x56 = (function () { function x56() { } + x56.member = [d1, d2]; return x56; }()); -x56.member = [d1, d2]; var x57 = (function () { function x57() { } + x57.member = [d1, d2]; return x57; }()); -x57.member = [d1, d2]; var x58 = (function () { function x58() { } + x58.member = { n: [d1, d2] }; return x58; }()); -x58.member = { n: [d1, d2] }; var x59 = (function () { function x59() { } + x59.member = function (n) { var n; return null; }; return x59; }()); -x59.member = function (n) { var n; return null; }; var x60 = (function () { function x60() { } + x60.member = { func: function (n) { return [d1, d2]; } }; return x60; }()); -x60.member = { func: function (n) { return [d1, d2]; } }; var x61 = (function () { function x61() { } + x61.member = function () { return [d1, d2]; }; return x61; }()); -x61.member = function () { return [d1, d2]; }; var x62 = (function () { function x62() { } + x62.member = function () { return [d1, d2]; }; return x62; }()); -x62.member = function () { return [d1, d2]; }; var x63 = (function () { function x63() { } + x63.member = function named() { return [d1, d2]; }; return x63; }()); -x63.member = function named() { return [d1, d2]; }; var x64 = (function () { function x64() { } + x64.member = function () { return [d1, d2]; }; return x64; }()); -x64.member = function () { return [d1, d2]; }; var x65 = (function () { function x65() { } + x65.member = function () { return [d1, d2]; }; return x65; }()); -x65.member = function () { return [d1, d2]; }; var x66 = (function () { function x66() { } + x66.member = function named() { return [d1, d2]; }; return x66; }()); -x66.member = function named() { return [d1, d2]; }; var x67 = (function () { function x67() { } + x67.member = [d1, d2]; return x67; }()); -x67.member = [d1, d2]; var x68 = (function () { function x68() { } + x68.member = [d1, d2]; return x68; }()); -x68.member = [d1, d2]; var x69 = (function () { function x69() { } + x69.member = [d1, d2]; return x69; }()); -x69.member = [d1, d2]; var x70 = (function () { function x70() { } + x70.member = { n: [d1, d2] }; return x70; }()); -x70.member = { n: [d1, d2] }; var x71 = (function () { function x71() { } + x71.member = function (n) { var n; return null; }; return x71; }()); -x71.member = function (n) { var n; return null; }; var x72 = (function () { function x72() { } + x72.member = { func: function (n) { return [d1, d2]; } }; return x72; }()); -x72.member = { func: function (n) { return [d1, d2]; } }; var x73 = (function () { function x73() { } + x73.member = function () { return [d1, d2]; }; return x73; }()); -x73.member = function () { return [d1, d2]; }; var x74 = (function () { function x74() { } + x74.member = function () { return [d1, d2]; }; return x74; }()); -x74.member = function () { return [d1, d2]; }; var x75 = (function () { function x75() { } + x75.member = function named() { return [d1, d2]; }; return x75; }()); -x75.member = function named() { return [d1, d2]; }; var x76 = (function () { function x76() { } + x76.member = function () { return [d1, d2]; }; return x76; }()); -x76.member = function () { return [d1, d2]; }; var x77 = (function () { function x77() { } + x77.member = function () { return [d1, d2]; }; return x77; }()); -x77.member = function () { return [d1, d2]; }; var x78 = (function () { function x78() { } + x78.member = function named() { return [d1, d2]; }; return x78; }()); -x78.member = function named() { return [d1, d2]; }; var x79 = (function () { function x79() { } + x79.member = [d1, d2]; return x79; }()); -x79.member = [d1, d2]; var x80 = (function () { function x80() { } + x80.member = [d1, d2]; return x80; }()); -x80.member = [d1, d2]; var x81 = (function () { function x81() { } + x81.member = [d1, d2]; return x81; }()); -x81.member = [d1, d2]; var x82 = (function () { function x82() { } + x82.member = { n: [d1, d2] }; return x82; }()); -x82.member = { n: [d1, d2] }; var x83 = (function () { function x83() { } + x83.member = function (n) { var n; return null; }; return x83; }()); -x83.member = function (n) { var n; return null; }; var x84 = (function () { function x84() { } + x84.member = { func: function (n) { return [d1, d2]; } }; return x84; }()); -x84.member = { func: function (n) { return [d1, d2]; } }; var x85 = (function () { function x85(parm) { if (parm === void 0) { parm = function () { return [d1, d2]; }; } diff --git a/tests/baselines/reference/genericClassWithStaticsUsingTypeArguments.js b/tests/baselines/reference/genericClassWithStaticsUsingTypeArguments.js index 053fa785ee0..2039e459572 100644 --- a/tests/baselines/reference/genericClassWithStaticsUsingTypeArguments.js +++ b/tests/baselines/reference/genericClassWithStaticsUsingTypeArguments.js @@ -25,9 +25,9 @@ var Foo = (function () { Foo.f = function (xs) { return xs.reverse(); }; + Foo.a = function (n) { }; + Foo.c = []; + Foo.d = false || (function (x) { return x || undefined; })(null); + Foo.e = function (x) { return null; }; return Foo; }()); -Foo.a = function (n) { }; -Foo.c = []; -Foo.d = false || (function (x) { return x || undefined; })(null); -Foo.e = function (x) { return null; }; diff --git a/tests/baselines/reference/gettersAndSetters.js b/tests/baselines/reference/gettersAndSetters.js index 265a1210b16..16d66c7dc71 100644 --- a/tests/baselines/reference/gettersAndSetters.js +++ b/tests/baselines/reference/gettersAndSetters.js @@ -65,9 +65,9 @@ var C = (function () { enumerable: true, configurable: true }); + C.barBack = ""; return C; }()); -C.barBack = ""; var c = new C(); var foo = c.Foo; c.Foo = "foov"; diff --git a/tests/baselines/reference/importHelpers.js b/tests/baselines/reference/importHelpers.js index bf66829a435..4fc7b99a813 100644 --- a/tests/baselines/reference/importHelpers.js +++ b/tests/baselines/reference/importHelpers.js @@ -56,17 +56,17 @@ var C = (function () { } C.prototype.method = function (x) { }; + tslib_1.__decorate([ + tslib_1.__param(0, dec), + tslib_1.__metadata("design:type", Function), + tslib_1.__metadata("design:paramtypes", [Number]), + tslib_1.__metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = tslib_1.__decorate([ + dec + ], C); return C; }()); -tslib_1.__decorate([ - tslib_1.__param(0, dec), - tslib_1.__metadata("design:type", Function), - tslib_1.__metadata("design:paramtypes", [Number]), - tslib_1.__metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = tslib_1.__decorate([ - dec -], C); //// [script.js] var __extends = (this && this.__extends) || (function () { var extendStatics = Object.setPrototypeOf || @@ -107,14 +107,14 @@ var C = (function () { } C.prototype.method = function (x) { }; + __decorate([ + __param(0, dec), + __metadata("design:type", Function), + __metadata("design:paramtypes", [Number]), + __metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = __decorate([ + dec + ], C); return C; }()); -__decorate([ - __param(0, dec), - __metadata("design:type", Function), - __metadata("design:paramtypes", [Number]), - __metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/importHelpersInIsolatedModules.js b/tests/baselines/reference/importHelpersInIsolatedModules.js index 26a9cafa188..561bfebb351 100644 --- a/tests/baselines/reference/importHelpersInIsolatedModules.js +++ b/tests/baselines/reference/importHelpersInIsolatedModules.js @@ -56,17 +56,17 @@ var C = (function () { } C.prototype.method = function (x) { }; + tslib_1.__decorate([ + tslib_1.__param(0, dec), + tslib_1.__metadata("design:type", Function), + tslib_1.__metadata("design:paramtypes", [Number]), + tslib_1.__metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = tslib_1.__decorate([ + dec + ], C); return C; }()); -tslib_1.__decorate([ - tslib_1.__param(0, dec), - tslib_1.__metadata("design:type", Function), - tslib_1.__metadata("design:paramtypes", [Number]), - tslib_1.__metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = tslib_1.__decorate([ - dec -], C); //// [script.js] var tslib_1 = require("tslib"); var A = (function () { @@ -86,14 +86,14 @@ var C = (function () { } C.prototype.method = function (x) { }; + tslib_1.__decorate([ + tslib_1.__param(0, dec), + tslib_1.__metadata("design:type", Function), + tslib_1.__metadata("design:paramtypes", [Number]), + tslib_1.__metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = tslib_1.__decorate([ + dec + ], C); return C; }()); -tslib_1.__decorate([ - tslib_1.__param(0, dec), - tslib_1.__metadata("design:type", Function), - tslib_1.__metadata("design:paramtypes", [Number]), - tslib_1.__metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = tslib_1.__decorate([ - dec -], C); diff --git a/tests/baselines/reference/importHelpersNoHelpers.js b/tests/baselines/reference/importHelpersNoHelpers.js index 5b98b61da20..9e20fc13543 100644 --- a/tests/baselines/reference/importHelpersNoHelpers.js +++ b/tests/baselines/reference/importHelpersNoHelpers.js @@ -55,17 +55,17 @@ var C = (function () { } C.prototype.method = function (x) { }; + tslib_1.__decorate([ + tslib_1.__param(0, dec), + tslib_1.__metadata("design:type", Function), + tslib_1.__metadata("design:paramtypes", [Number]), + tslib_1.__metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = tslib_1.__decorate([ + dec + ], C); return C; }()); -tslib_1.__decorate([ - tslib_1.__param(0, dec), - tslib_1.__metadata("design:type", Function), - tslib_1.__metadata("design:paramtypes", [Number]), - tslib_1.__metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = tslib_1.__decorate([ - dec -], C); var o = { a: 1 }; var y = tslib_1.__assign({}, o); var x = tslib_1.__rest(y, []); @@ -109,14 +109,14 @@ var C = (function () { } C.prototype.method = function (x) { }; + __decorate([ + __param(0, dec), + __metadata("design:type", Function), + __metadata("design:paramtypes", [Number]), + __metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = __decorate([ + dec + ], C); return C; }()); -__decorate([ - __param(0, dec), - __metadata("design:type", Function), - __metadata("design:paramtypes", [Number]), - __metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/importHelpersNoModule.js b/tests/baselines/reference/importHelpersNoModule.js index 36a326e124d..988bec04a42 100644 --- a/tests/baselines/reference/importHelpersNoModule.js +++ b/tests/baselines/reference/importHelpersNoModule.js @@ -48,17 +48,17 @@ var C = (function () { } C.prototype.method = function (x) { }; + tslib_1.__decorate([ + tslib_1.__param(0, dec), + tslib_1.__metadata("design:type", Function), + tslib_1.__metadata("design:paramtypes", [Number]), + tslib_1.__metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = tslib_1.__decorate([ + dec + ], C); return C; }()); -tslib_1.__decorate([ - tslib_1.__param(0, dec), - tslib_1.__metadata("design:type", Function), - tslib_1.__metadata("design:paramtypes", [Number]), - tslib_1.__metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = tslib_1.__decorate([ - dec -], C); //// [script.js] var __extends = (this && this.__extends) || (function () { var extendStatics = Object.setPrototypeOf || @@ -99,14 +99,14 @@ var C = (function () { } C.prototype.method = function (x) { }; + __decorate([ + __param(0, dec), + __metadata("design:type", Function), + __metadata("design:paramtypes", [Number]), + __metadata("design:returntype", void 0) + ], C.prototype, "method", null); + C = __decorate([ + dec + ], C); return C; }()); -__decorate([ - __param(0, dec), - __metadata("design:type", Function), - __metadata("design:paramtypes", [Number]), - __metadata("design:returntype", void 0) -], C.prototype, "method", null); -C = __decorate([ - dec -], C); diff --git a/tests/baselines/reference/importImportOnlyModule.js b/tests/baselines/reference/importImportOnlyModule.js index 0c6f0540354..fa01655c47b 100644 --- a/tests/baselines/reference/importImportOnlyModule.js +++ b/tests/baselines/reference/importImportOnlyModule.js @@ -23,9 +23,9 @@ define(["require", "exports"], function (require, exports) { function C1() { this.m1 = 42; } + C1.s1 = true; return C1; }()); - C1.s1 = true; exports.C1 = C1; }); //// [foo_1.js] diff --git a/tests/baselines/reference/inferringClassMembersFromAssignments.js b/tests/baselines/reference/inferringClassMembersFromAssignments.js index 1c1f223abe8..c6a6d0c4e27 100644 --- a/tests/baselines/reference/inferringClassMembersFromAssignments.js +++ b/tests/baselines/reference/inferringClassMembersFromAssignments.js @@ -124,7 +124,6 @@ var stringOrNumberOrUndefined = C.inStaticNestedArrowFunction; //// [output.js] -var _this = this; var C = (function () { function C() { var _this = this; @@ -212,16 +211,16 @@ var C = (function () { this.inStaticSetter = "string"; } }; + C.prop = function () { + if (Math.random()) { + _this.inStaticPropertyDeclaration = 0; + } + else { + _this.inStaticPropertyDeclaration = "string"; + } + }; return C; }()); -C.prop = function () { - if (Math.random()) { - _this.inStaticPropertyDeclaration = 0; - } - else { - _this.inStaticPropertyDeclaration = "string"; - } -}; var c = new C(); var stringOrNumber; var stringOrNumber = c.inConstructor; diff --git a/tests/baselines/reference/instanceAndStaticDeclarations1.js b/tests/baselines/reference/instanceAndStaticDeclarations1.js index bf9b6963bb2..093e9c15cc8 100644 --- a/tests/baselines/reference/instanceAndStaticDeclarations1.js +++ b/tests/baselines/reference/instanceAndStaticDeclarations1.js @@ -25,6 +25,6 @@ var Point = (function () { return Math.sqrt(dx * dx + dy * dy); }; Point.distance = function (p1, p2) { return p1.distance(p2); }; + Point.origin = new Point(0, 0); return Point; }()); -Point.origin = new Point(0, 0); diff --git a/tests/baselines/reference/invalidNewTarget.es5.js b/tests/baselines/reference/invalidNewTarget.es5.js index 866dac270af..1c2da520fcb 100644 --- a/tests/baselines/reference/invalidNewTarget.es5.js +++ b/tests/baselines/reference/invalidNewTarget.es5.js @@ -56,9 +56,9 @@ var C = (function () { enumerable: true, configurable: true }); + C.j = function () { return _newTarget; }; return C; }()); -C.j = function () { return _newTarget; }; var O = (_a = {}, _a[_newTarget] = undefined, _a.k = function () { var _newTarget = void 0; return _newTarget; }, diff --git a/tests/baselines/reference/invalidStaticField.js b/tests/baselines/reference/invalidStaticField.js index 08a06d5ee27..dc582e830c7 100644 --- a/tests/baselines/reference/invalidStaticField.js +++ b/tests/baselines/reference/invalidStaticField.js @@ -12,6 +12,6 @@ var A = (function () { var B = (function () { function B() { } + B.NOT_NULL = new B(); return B; }()); -B.NOT_NULL = new B(); diff --git a/tests/baselines/reference/metadataOfClassFromAlias.js b/tests/baselines/reference/metadataOfClassFromAlias.js index c99f7cc2e23..75fdd90652f 100644 --- a/tests/baselines/reference/metadataOfClassFromAlias.js +++ b/tests/baselines/reference/metadataOfClassFromAlias.js @@ -41,10 +41,10 @@ function annotation() { var ClassA = (function () { function ClassA() { } + __decorate([ + annotation(), + __metadata("design:type", Object) + ], ClassA.prototype, "array", void 0); return ClassA; }()); -__decorate([ - annotation(), - __metadata("design:type", Object) -], ClassA.prototype, "array", void 0); exports.ClassA = ClassA; diff --git a/tests/baselines/reference/metadataOfClassFromAlias2.js b/tests/baselines/reference/metadataOfClassFromAlias2.js index bcdbb34ac50..ca568028638 100644 --- a/tests/baselines/reference/metadataOfClassFromAlias2.js +++ b/tests/baselines/reference/metadataOfClassFromAlias2.js @@ -41,10 +41,10 @@ function annotation() { var ClassA = (function () { function ClassA() { } + __decorate([ + annotation(), + __metadata("design:type", Object) + ], ClassA.prototype, "array", void 0); return ClassA; }()); -__decorate([ - annotation(), - __metadata("design:type", Object) -], ClassA.prototype, "array", void 0); exports.ClassA = ClassA; diff --git a/tests/baselines/reference/metadataOfClassFromModule.js b/tests/baselines/reference/metadataOfClassFromModule.js index 8ef120600df..ca8c56e3c5e 100644 --- a/tests/baselines/reference/metadataOfClassFromModule.js +++ b/tests/baselines/reference/metadataOfClassFromModule.js @@ -34,11 +34,11 @@ var MyModule; var Person = (function () { function Person() { } + __decorate([ + inject, + __metadata("design:type", Leg) + ], Person.prototype, "leftLeg", void 0); return Person; }()); - __decorate([ - inject, - __metadata("design:type", Leg) - ], Person.prototype, "leftLeg", void 0); MyModule.Person = Person; })(MyModule || (MyModule = {})); diff --git a/tests/baselines/reference/metadataOfEventAlias.js b/tests/baselines/reference/metadataOfEventAlias.js index b46d5cade63..cf042586242 100644 --- a/tests/baselines/reference/metadataOfEventAlias.js +++ b/tests/baselines/reference/metadataOfEventAlias.js @@ -30,10 +30,10 @@ function Input(target, key) { } var SomeClass = (function () { function SomeClass() { } + __decorate([ + Input, + __metadata("design:type", Object) + ], SomeClass.prototype, "event", void 0); return SomeClass; }()); -__decorate([ - Input, - __metadata("design:type", Object) -], SomeClass.prototype, "event", void 0); exports.SomeClass = SomeClass; diff --git a/tests/baselines/reference/metadataOfStringLiteral.js b/tests/baselines/reference/metadataOfStringLiteral.js index 676914681cb..30536270207 100644 --- a/tests/baselines/reference/metadataOfStringLiteral.js +++ b/tests/baselines/reference/metadataOfStringLiteral.js @@ -20,9 +20,9 @@ function PropDeco(target, propKey) { } var Foo = (function () { function Foo() { } + __decorate([ + PropDeco, + __metadata("design:type", String) + ], Foo.prototype, "foo"); return Foo; }()); -__decorate([ - PropDeco, - __metadata("design:type", String) -], Foo.prototype, "foo"); diff --git a/tests/baselines/reference/metadataOfUnion.js b/tests/baselines/reference/metadataOfUnion.js index 9a88481c80a..7a063b0e93c 100644 --- a/tests/baselines/reference/metadataOfUnion.js +++ b/tests/baselines/reference/metadataOfUnion.js @@ -55,20 +55,20 @@ var A = (function () { var B = (function () { function B() { } + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "x"); + __decorate([ + PropDeco, + __metadata("design:type", Boolean) + ], B.prototype, "y"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "z"); return B; }()); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "x"); -__decorate([ - PropDeco, - __metadata("design:type", Boolean) -], B.prototype, "y"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "z"); var E; (function (E) { E[E["A"] = 0] = "A"; @@ -79,21 +79,21 @@ var E; var D = (function () { function D() { } + __decorate([ + PropDeco, + __metadata("design:type", Number) + ], D.prototype, "a"); + __decorate([ + PropDeco, + __metadata("design:type", Number) + ], D.prototype, "b"); + __decorate([ + PropDeco, + __metadata("design:type", Number) + ], D.prototype, "c"); + __decorate([ + PropDeco, + __metadata("design:type", Number) + ], D.prototype, "d"); return D; }()); -__decorate([ - PropDeco, - __metadata("design:type", Number) -], D.prototype, "a"); -__decorate([ - PropDeco, - __metadata("design:type", Number) -], D.prototype, "b"); -__decorate([ - PropDeco, - __metadata("design:type", Number) -], D.prototype, "c"); -__decorate([ - PropDeco, - __metadata("design:type", Number) -], D.prototype, "d"); diff --git a/tests/baselines/reference/metadataOfUnionWithNull.js b/tests/baselines/reference/metadataOfUnionWithNull.js index 0c834be9687..e53ca85476e 100644 --- a/tests/baselines/reference/metadataOfUnionWithNull.js +++ b/tests/baselines/reference/metadataOfUnionWithNull.js @@ -61,53 +61,53 @@ var A = (function () { var B = (function () { function B() { } + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "x"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "y"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "z"); + __decorate([ + PropDeco, + __metadata("design:type", void 0) + ], B.prototype, "a"); + __decorate([ + PropDeco, + __metadata("design:type", void 0) + ], B.prototype, "b"); + __decorate([ + PropDeco, + __metadata("design:type", void 0) + ], B.prototype, "c"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "d"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "e"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "f"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "g"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "h"); + __decorate([ + PropDeco, + __metadata("design:type", Object) + ], B.prototype, "j"); return B; }()); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "x"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "y"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "z"); -__decorate([ - PropDeco, - __metadata("design:type", void 0) -], B.prototype, "a"); -__decorate([ - PropDeco, - __metadata("design:type", void 0) -], B.prototype, "b"); -__decorate([ - PropDeco, - __metadata("design:type", void 0) -], B.prototype, "c"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "d"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "e"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "f"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "g"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "h"); -__decorate([ - PropDeco, - __metadata("design:type", Object) -], B.prototype, "j"); diff --git a/tests/baselines/reference/missingDecoratorType.js b/tests/baselines/reference/missingDecoratorType.js index ee9fbf7ce44..eca16c710e3 100644 --- a/tests/baselines/reference/missingDecoratorType.js +++ b/tests/baselines/reference/missingDecoratorType.js @@ -32,8 +32,8 @@ var C = (function () { function C() { } C.prototype.method = function () { }; + __decorate([ + dec + ], C.prototype, "method", null); return C; }()); -__decorate([ - dec -], C.prototype, "method", null); diff --git a/tests/baselines/reference/newTarget.es5.js b/tests/baselines/reference/newTarget.es5.js index 2ebe4bfcadc..38718a771ad 100644 --- a/tests/baselines/reference/newTarget.es5.js +++ b/tests/baselines/reference/newTarget.es5.js @@ -50,9 +50,9 @@ var A = (function () { var a = _newTarget; var b = function () { return _newTarget; }; } + A.c = function _a() { var _newTarget = this && this instanceof _a ? this.constructor : void 0; return _newTarget; }; return A; }()); -A.c = function _a() { var _newTarget = this && this instanceof _a ? this.constructor : void 0; return _newTarget; }; var B = (function (_super) { __extends(B, _super); function B() { @@ -69,11 +69,11 @@ function f1() { var g = _newTarget; var h = function () { return _newTarget; }; } -var f2 = function _b() { - var _newTarget = this && this instanceof _b ? this.constructor : void 0; +var f2 = function _a() { + var _newTarget = this && this instanceof _a ? this.constructor : void 0; var i = _newTarget; var j = function () { return _newTarget; }; }; var O = { - k: function _c() { var _newTarget = this && this instanceof _c ? this.constructor : void 0; return _newTarget; } + k: function _b() { var _newTarget = this && this instanceof _b ? this.constructor : void 0; return _newTarget; } }; diff --git a/tests/baselines/reference/noEmitHelpers2.js b/tests/baselines/reference/noEmitHelpers2.js index 44ab7900005..027f07cc0e8 100644 --- a/tests/baselines/reference/noEmitHelpers2.js +++ b/tests/baselines/reference/noEmitHelpers2.js @@ -11,10 +11,10 @@ class A { var A = (function () { function A(a, b) { } + A = __decorate([ + decorator, + __param(1, decorator), + __metadata("design:paramtypes", [Number, String]) + ], A); return A; }()); -A = __decorate([ - decorator, - __param(1, decorator), - __metadata("design:paramtypes", [Number, String]) -], A); diff --git a/tests/baselines/reference/parserAccessibilityAfterStatic3.js b/tests/baselines/reference/parserAccessibilityAfterStatic3.js index 38202bc5dc8..7a9ae06e439 100644 --- a/tests/baselines/reference/parserAccessibilityAfterStatic3.js +++ b/tests/baselines/reference/parserAccessibilityAfterStatic3.js @@ -9,6 +9,6 @@ static public = 1; var Outer = (function () { function Outer() { } + Outer.public = 1; return Outer; }()); -Outer.public = 1; diff --git a/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable1.js b/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable1.js index 57d0536e975..9bb4395e556 100644 --- a/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable1.js +++ b/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable1.js @@ -41,10 +41,10 @@ var Shapes; } // Instance member Point.prototype.getDist = function () { return Math.sqrt(this.x * this.x + this.y * this.y); }; + // Static member + Point.origin = new Point(0, 0); return Point; }()); - // Static member - Point.origin = new Point(0, 0); Shapes.Point = Point; })(Shapes || (Shapes = {})); // Local variables diff --git a/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable2.js b/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable2.js index 2bb08a14e35..0ee73b8b1e5 100644 --- a/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable2.js +++ b/tests/baselines/reference/parserErrorRecovery_IncompleteMemberVariable2.js @@ -42,10 +42,10 @@ var Shapes; } // Instance member Point.prototype.getDist = function () { return Math.sqrt(this.x * this.x + this.y * this.y); }; + // Static member + Point.origin = new Point(0, 0); return Point; }()); - // Static member - Point.origin = new Point(0, 0); Shapes.Point = Point; })(Shapes || (Shapes = {})); // Local variables diff --git a/tests/baselines/reference/parserharness.js b/tests/baselines/reference/parserharness.js index 5090c33bdc8..2275a1f682e 100644 --- a/tests/baselines/reference/parserharness.js +++ b/tests/baselines/reference/parserharness.js @@ -2376,11 +2376,11 @@ var Harness; errorHandlerStack[errorHandlerStack.length - 1](e); } }; + // The current stack of Runnable objects + Runnable.currentStack = []; + Runnable.errorHandlerStack = []; return Runnable; }()); - // The current stack of Runnable objects - Runnable.currentStack = []; - Runnable.errorHandlerStack = []; Harness.Runnable = Runnable; var TestCase = (function (_super) { __extends(TestCase, _super); diff --git a/tests/baselines/reference/privacyCannotNameVarTypeDeclFile.js b/tests/baselines/reference/privacyCannotNameVarTypeDeclFile.js index 9da4e922f77..da23223510c 100644 --- a/tests/baselines/reference/privacyCannotNameVarTypeDeclFile.js +++ b/tests/baselines/reference/privacyCannotNameVarTypeDeclFile.js @@ -160,12 +160,12 @@ var publicClassWithWithPrivatePropertyTypes = (function () { this.myPublicProperty1 = exporter.createExportedWidget3(); // Error this.myPrivateProperty1 = exporter.createExportedWidget3(); } + publicClassWithWithPrivatePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget1(); // Error + publicClassWithWithPrivatePropertyTypes.myPrivateStaticProperty = exporter.createExportedWidget1(); + publicClassWithWithPrivatePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget3(); // Error + publicClassWithWithPrivatePropertyTypes.myPrivateStaticProperty1 = exporter.createExportedWidget3(); return publicClassWithWithPrivatePropertyTypes; }()); -publicClassWithWithPrivatePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget1(); // Error -publicClassWithWithPrivatePropertyTypes.myPrivateStaticProperty = exporter.createExportedWidget1(); -publicClassWithWithPrivatePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget3(); // Error -publicClassWithWithPrivatePropertyTypes.myPrivateStaticProperty1 = exporter.createExportedWidget3(); exports.publicClassWithWithPrivatePropertyTypes = publicClassWithWithPrivatePropertyTypes; var privateClassWithWithPrivatePropertyTypes = (function () { function privateClassWithWithPrivatePropertyTypes() { @@ -174,12 +174,12 @@ var privateClassWithWithPrivatePropertyTypes = (function () { this.myPublicProperty1 = exporter.createExportedWidget3(); this.myPrivateProperty1 = exporter.createExportedWidget3(); } + privateClassWithWithPrivatePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget1(); + privateClassWithWithPrivatePropertyTypes.myPrivateStaticProperty = exporter.createExportedWidget1(); + privateClassWithWithPrivatePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget3(); + privateClassWithWithPrivatePropertyTypes.myPrivateStaticProperty1 = exporter.createExportedWidget3(); return privateClassWithWithPrivatePropertyTypes; }()); -privateClassWithWithPrivatePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget1(); -privateClassWithWithPrivatePropertyTypes.myPrivateStaticProperty = exporter.createExportedWidget1(); -privateClassWithWithPrivatePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget3(); -privateClassWithWithPrivatePropertyTypes.myPrivateStaticProperty1 = exporter.createExportedWidget3(); exports.publicVarWithPrivatePropertyTypes = exporter.createExportedWidget1(); // Error var privateVarWithPrivatePropertyTypes = exporter.createExportedWidget1(); exports.publicVarWithPrivatePropertyTypes1 = exporter.createExportedWidget3(); // Error @@ -189,10 +189,10 @@ var publicClassWithPrivateModulePropertyTypes = (function () { this.myPublicProperty = exporter.createExportedWidget2(); // Error this.myPublicProperty1 = exporter.createExportedWidget4(); // Error } + publicClassWithPrivateModulePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget2(); // Error + publicClassWithPrivateModulePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget4(); // Error return publicClassWithPrivateModulePropertyTypes; }()); -publicClassWithPrivateModulePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget2(); // Error -publicClassWithPrivateModulePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget4(); // Error exports.publicClassWithPrivateModulePropertyTypes = publicClassWithPrivateModulePropertyTypes; exports.publicVarWithPrivateModulePropertyTypes = exporter.createExportedWidget2(); // Error exports.publicVarWithPrivateModulePropertyTypes1 = exporter.createExportedWidget4(); // Error @@ -201,10 +201,10 @@ var privateClassWithPrivateModulePropertyTypes = (function () { this.myPublicProperty = exporter.createExportedWidget2(); this.myPublicProperty1 = exporter.createExportedWidget4(); } + privateClassWithPrivateModulePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget2(); + privateClassWithPrivateModulePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget4(); return privateClassWithPrivateModulePropertyTypes; }()); -privateClassWithPrivateModulePropertyTypes.myPublicStaticProperty = exporter.createExportedWidget2(); -privateClassWithPrivateModulePropertyTypes.myPublicStaticProperty1 = exporter.createExportedWidget4(); var privateVarWithPrivateModulePropertyTypes = exporter.createExportedWidget2(); var privateVarWithPrivateModulePropertyTypes1 = exporter.createExportedWidget4(); diff --git a/tests/baselines/reference/privateStaticMemberAccessibility.js b/tests/baselines/reference/privateStaticMemberAccessibility.js index 92a8713ef8f..aca72ba86e5 100644 --- a/tests/baselines/reference/privateStaticMemberAccessibility.js +++ b/tests/baselines/reference/privateStaticMemberAccessibility.js @@ -31,6 +31,6 @@ var Derived = (function (_super) { _this.bing = function () { return Base.foo; }; // error return _this; } + Derived.bar = Base.foo; // error return Derived; }(Base)); -Derived.bar = Base.foo; // error diff --git a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/amd/main.js b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/amd/main.js index 6ec26abec8e..f1d17701cf8 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/amd/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/amd/main.js @@ -14,12 +14,12 @@ define(["require", "exports", "angular2/core"], function (require, exports, ng) function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); exports.MyClass1 = MyClass1; - var _a; }); diff --git a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/node/main.js b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/node/main.js index 274520bc752..c7191f0e4c6 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/node/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModules/node/main.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); exports.MyClass1 = MyClass1; -var _a; diff --git a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/amd/main.js b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/amd/main.js index 6ec26abec8e..f1d17701cf8 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/amd/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/amd/main.js @@ -14,12 +14,12 @@ define(["require", "exports", "angular2/core"], function (require, exports, ng) function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); exports.MyClass1 = MyClass1; - var _a; }); diff --git a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/node/main.js b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/node/main.js index 274520bc752..c7191f0e4c6 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/node/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataCommonJSISolatedModulesNoResolve/node/main.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); exports.MyClass1 = MyClass1; -var _a; diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/amd/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/amd/main.js index 6ec26abec8e..f1d17701cf8 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/amd/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/amd/main.js @@ -14,12 +14,12 @@ define(["require", "exports", "angular2/core"], function (require, exports, ng) function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); exports.MyClass1 = MyClass1; - var _a; }); diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/node/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/node/main.js index 274520bc752..c7191f0e4c6 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/node/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJS/node/main.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); exports.MyClass1 = MyClass1; -var _a; diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/amd/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/amd/main.js index 6ec26abec8e..f1d17701cf8 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/amd/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/amd/main.js @@ -14,12 +14,12 @@ define(["require", "exports", "angular2/core"], function (require, exports, ng) function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); exports.MyClass1 = MyClass1; - var _a; }); diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/node/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/node/main.js index 274520bc752..c7191f0e4c6 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/node/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModules/node/main.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); exports.MyClass1 = MyClass1; -var _a; diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/amd/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/amd/main.js index 6ec26abec8e..f1d17701cf8 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/amd/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/amd/main.js @@ -14,12 +14,12 @@ define(["require", "exports", "angular2/core"], function (require, exports, ng) function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); exports.MyClass1 = MyClass1; - var _a; }); diff --git a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/node/main.js b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/node/main.js index 274520bc752..c7191f0e4c6 100644 --- a/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/node/main.js +++ b/tests/baselines/reference/project/emitDecoratorMetadataSystemJSISolatedModulesNoResolve/node/main.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + foo, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - foo, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); exports.MyClass1 = MyClass1; -var _a; diff --git a/tests/baselines/reference/propertyAccessibility2.js b/tests/baselines/reference/propertyAccessibility2.js index 3618b86fcc5..afce6c4c24a 100644 --- a/tests/baselines/reference/propertyAccessibility2.js +++ b/tests/baselines/reference/propertyAccessibility2.js @@ -9,7 +9,7 @@ var c = C.x; var C = (function () { function C() { } + C.x = 1; return C; }()); -C.x = 1; var c = C.x; diff --git a/tests/baselines/reference/quotedPropertyName2.js b/tests/baselines/reference/quotedPropertyName2.js index 550e5299702..1c4d85076ea 100644 --- a/tests/baselines/reference/quotedPropertyName2.js +++ b/tests/baselines/reference/quotedPropertyName2.js @@ -7,6 +7,6 @@ class Test1 { var Test1 = (function () { function Test1() { } + Test1["prop1"] = 0; return Test1; }()); -Test1["prop1"] = 0; diff --git a/tests/baselines/reference/reassignStaticProp.js b/tests/baselines/reference/reassignStaticProp.js index d9c37c29ad5..2bf2bafa128 100644 --- a/tests/baselines/reference/reassignStaticProp.js +++ b/tests/baselines/reference/reassignStaticProp.js @@ -15,6 +15,6 @@ class foo { var foo = (function () { function foo() { } + foo.bar = 1; return foo; }()); -foo.bar = 1; diff --git a/tests/baselines/reference/scopeCheckStaticInitializer.js b/tests/baselines/reference/scopeCheckStaticInitializer.js index 59711f07380..a9478d44800 100644 --- a/tests/baselines/reference/scopeCheckStaticInitializer.js +++ b/tests/baselines/reference/scopeCheckStaticInitializer.js @@ -20,18 +20,18 @@ var X = (function () { function X() { } X.method = function () { }; + X.illegalBeforeProperty = X.data; + X.okBeforeMethod = X.method; + X.illegal2 = After.data; + X.illegal3 = After.method; + X.data = 13; return X; }()); -X.illegalBeforeProperty = X.data; -X.okBeforeMethod = X.method; -X.illegal2 = After.data; -X.illegal3 = After.method; -X.data = 13; var After = (function () { function After() { } After.method = function () { }; ; + After.data = 12; return After; }()); -After.data = 12; diff --git a/tests/baselines/reference/sourceMap-FileWithComments.js b/tests/baselines/reference/sourceMap-FileWithComments.js index d2287d0bea2..7fd47997c97 100644 --- a/tests/baselines/reference/sourceMap-FileWithComments.js +++ b/tests/baselines/reference/sourceMap-FileWithComments.js @@ -48,10 +48,10 @@ var Shapes; } // Instance member Point.prototype.getDist = function () { return Math.sqrt(this.x * this.x + this.y * this.y); }; + // Static member + Point.origin = new Point(0, 0); return Point; }()); - // Static member - Point.origin = new Point(0, 0); Shapes.Point = Point; // Variable comment after class var a = 10; diff --git a/tests/baselines/reference/sourceMap-FileWithComments.js.map b/tests/baselines/reference/sourceMap-FileWithComments.js.map index a85ce154f11..073fa862fc7 100644 --- a/tests/baselines/reference/sourceMap-FileWithComments.js.map +++ b/tests/baselines/reference/sourceMap-FileWithComments.js.map @@ -1,2 +1,2 @@ //// [sourceMap-FileWithComments.js.map] -{"version":3,"file":"sourceMap-FileWithComments.js","sourceRoot":"","sources":["sourceMap-FileWithComments.ts"],"names":[],"mappings":"AAKA,SAAS;AACT,IAAO,MAAM,CAwBZ;AAxBD,WAAO,MAAM;IAET,QAAQ;IACR;QACI,cAAc;QACd,eAAmB,CAAS,EAAS,CAAS;YAA3B,MAAC,GAAD,CAAC,CAAQ;YAAS,MAAC,GAAD,CAAC,CAAQ;QAAI,CAAC;QAEnD,kBAAkB;QAClB,uBAAO,GAAP,cAAY,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAItE,YAAC;IAAD,CAAC,AATD;IAOI,gBAAgB;IACT,YAAM,GAAG,IAAI,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IARvB,YAAK,QASjB,CAAA;IAED,+BAA+B;IAC/B,IAAI,CAAC,GAAG,EAAE,CAAC;IAEX;IACA,CAAC;IADe,UAAG,MAClB,CAAA;IAED;;MAEE;IACF,IAAI,CAAC,GAAG,EAAE,CAAC;AACf,CAAC,EAxBM,MAAM,KAAN,MAAM,QAwBZ;AAED,qBAAqB;AACrB,IAAI,CAAC,GAAW,IAAI,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;AACvC,IAAI,IAAI,GAAG,CAAC,CAAC,OAAO,EAAE,CAAC"} \ No newline at end of file +{"version":3,"file":"sourceMap-FileWithComments.js","sourceRoot":"","sources":["sourceMap-FileWithComments.ts"],"names":[],"mappings":"AAKA,SAAS;AACT,IAAO,MAAM,CAwBZ;AAxBD,WAAO,MAAM;IAET,QAAQ;IACR;QACI,cAAc;QACd,eAAmB,CAAS,EAAS,CAAS;YAA3B,MAAC,GAAD,CAAC,CAAQ;YAAS,MAAC,GAAD,CAAC,CAAQ;QAAI,CAAC;QAEnD,kBAAkB;QAClB,uBAAO,GAAP,cAAY,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAElE,gBAAgB;QACT,YAAM,GAAG,IAAI,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;QACpC,YAAC;KAAA,AATD,IASC;IATY,YAAK,QASjB,CAAA;IAED,+BAA+B;IAC/B,IAAI,CAAC,GAAG,EAAE,CAAC;IAEX;IACA,CAAC;IADe,UAAG,MAClB,CAAA;IAED;;MAEE;IACF,IAAI,CAAC,GAAG,EAAE,CAAC;AACf,CAAC,EAxBM,MAAM,KAAN,MAAM,QAwBZ;AAED,qBAAqB;AACrB,IAAI,CAAC,GAAW,IAAI,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;AACvC,IAAI,IAAI,GAAG,CAAC,CAAC,OAAO,EAAE,CAAC"} \ No newline at end of file diff --git a/tests/baselines/reference/sourceMap-FileWithComments.sourcemap.txt b/tests/baselines/reference/sourceMap-FileWithComments.sourcemap.txt index 9e81aba718a..b53a0a4a7ce 100644 --- a/tests/baselines/reference/sourceMap-FileWithComments.sourcemap.txt +++ b/tests/baselines/reference/sourceMap-FileWithComments.sourcemap.txt @@ -264,89 +264,90 @@ sourceFile:sourceMap-FileWithComments.ts 28>Emitted(12, 102) Source(15, 74) + SourceIndex(0) 29>Emitted(12, 103) Source(15, 75) + SourceIndex(0) --- +>>> // Static member +1 >^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^-> +1 > + > + > +2 > // Static member +1 >Emitted(13, 9) Source(17, 9) + SourceIndex(0) +2 >Emitted(13, 25) Source(17, 25) + SourceIndex(0) +--- +>>> Point.origin = new Point(0, 0); +1->^^^^^^^^ +2 > ^^^^^^^^^^^^ +3 > ^^^ +4 > ^^^^ +5 > ^^^^^ +6 > ^ +7 > ^ +8 > ^^ +9 > ^ +10> ^ +11> ^ +1-> + > static +2 > origin +3 > = +4 > new +5 > Point +6 > ( +7 > 0 +8 > , +9 > 0 +10> ) +11> ; +1->Emitted(14, 9) Source(18, 16) + SourceIndex(0) +2 >Emitted(14, 21) Source(18, 22) + SourceIndex(0) +3 >Emitted(14, 24) Source(18, 25) + SourceIndex(0) +4 >Emitted(14, 28) Source(18, 29) + SourceIndex(0) +5 >Emitted(14, 33) Source(18, 34) + SourceIndex(0) +6 >Emitted(14, 34) Source(18, 35) + SourceIndex(0) +7 >Emitted(14, 35) Source(18, 36) + SourceIndex(0) +8 >Emitted(14, 37) Source(18, 38) + SourceIndex(0) +9 >Emitted(14, 38) Source(18, 39) + SourceIndex(0) +10>Emitted(14, 39) Source(18, 40) + SourceIndex(0) +11>Emitted(14, 40) Source(18, 41) + SourceIndex(0) +--- >>> return Point; 1 >^^^^^^^^ 2 > ^^^^^^^^^^^^ 1 > - > - > // Static member - > static origin = new Point(0, 0); > 2 > } -1 >Emitted(13, 9) Source(19, 5) + SourceIndex(0) -2 >Emitted(13, 21) Source(19, 6) + SourceIndex(0) +1 >Emitted(15, 9) Source(19, 5) + SourceIndex(0) +2 >Emitted(15, 21) Source(19, 6) + SourceIndex(0) --- >>> }()); -1 >^^^^ -2 > ^ -3 > -4 > ^^^^^^^^^^^^^^^^-> +1 >^^^^^ +2 > +3 > ^^^^ +4 > ^^^^^^^^^^^^^^^^^-> 1 > -2 > } -3 > -1 >Emitted(14, 5) Source(19, 5) + SourceIndex(0) -2 >Emitted(14, 6) Source(19, 6) + SourceIndex(0) -3 >Emitted(14, 6) Source(10, 5) + SourceIndex(0) ---- ->>> // Static member -1->^^^^ -2 > ^^^^^^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^-> -1->export class Point implements IPoint { - > // Constructor - > constructor(public x: number, public y: number) { } - > - > // Instance member - > getDist() { return Math.sqrt(this.x * this.x + this.y * this.y); } - > - > -2 > // Static member -1->Emitted(15, 5) Source(17, 9) + SourceIndex(0) -2 >Emitted(15, 21) Source(17, 25) + SourceIndex(0) ---- ->>> Point.origin = new Point(0, 0); -1->^^^^ -2 > ^^^^^^^^^^^^ -3 > ^^^ -4 > ^^^^ -5 > ^^^^^ -6 > ^ -7 > ^ -8 > ^^ -9 > ^ -10> ^ -11> ^ -1-> - > static -2 > origin -3 > = -4 > new -5 > Point -6 > ( -7 > 0 -8 > , -9 > 0 -10> ) -11> ; -1->Emitted(16, 5) Source(18, 16) + SourceIndex(0) -2 >Emitted(16, 17) Source(18, 22) + SourceIndex(0) -3 >Emitted(16, 20) Source(18, 25) + SourceIndex(0) -4 >Emitted(16, 24) Source(18, 29) + SourceIndex(0) -5 >Emitted(16, 29) Source(18, 34) + SourceIndex(0) -6 >Emitted(16, 30) Source(18, 35) + SourceIndex(0) -7 >Emitted(16, 31) Source(18, 36) + SourceIndex(0) -8 >Emitted(16, 33) Source(18, 38) + SourceIndex(0) -9 >Emitted(16, 34) Source(18, 39) + SourceIndex(0) -10>Emitted(16, 35) Source(18, 40) + SourceIndex(0) -11>Emitted(16, 36) Source(18, 41) + SourceIndex(0) +2 > +3 > export class Point implements IPoint { + > // Constructor + > constructor(public x: number, public y: number) { } + > + > // Instance member + > getDist() { return Math.sqrt(this.x * this.x + this.y * this.y); } + > + > // Static member + > static origin = new Point(0, 0); + > } +1 >Emitted(16, 6) Source(19, 6) + SourceIndex(0) +2 >Emitted(16, 6) Source(10, 5) + SourceIndex(0) +3 >Emitted(16, 10) Source(19, 6) + SourceIndex(0) --- >>> Shapes.Point = Point; -1 >^^^^ +1->^^^^ 2 > ^^^^^^^^^^^^ 3 > ^^^^^^^^ 4 > ^ 5 > ^^^^^^^^^^^-> -1 > +1-> 2 > Point 3 > implements IPoint { > // Constructor @@ -359,7 +360,7 @@ sourceFile:sourceMap-FileWithComments.ts > static origin = new Point(0, 0); > } 4 > -1 >Emitted(17, 5) Source(10, 18) + SourceIndex(0) +1->Emitted(17, 5) Source(10, 18) + SourceIndex(0) 2 >Emitted(17, 17) Source(10, 23) + SourceIndex(0) 3 >Emitted(17, 25) Source(19, 6) + SourceIndex(0) 4 >Emitted(17, 26) Source(19, 6) + SourceIndex(0) diff --git a/tests/baselines/reference/sourceMapValidationDecorators.js b/tests/baselines/reference/sourceMapValidationDecorators.js index 63cdb25900c..c3bb5cd7225 100644 --- a/tests/baselines/reference/sourceMapValidationDecorators.js +++ b/tests/baselines/reference/sourceMapValidationDecorators.js @@ -88,37 +88,37 @@ var Greeter = (function () { enumerable: true, configurable: true }); + Greeter.x1 = 10; + __decorate([ + PropertyDecorator1, + PropertyDecorator2(40) + ], Greeter.prototype, "greet", null); + __decorate([ + PropertyDecorator1, + PropertyDecorator2(50) + ], Greeter.prototype, "x", void 0); + __decorate([ + __param(0, ParameterDecorator1), + __param(0, ParameterDecorator2(70)) + ], Greeter.prototype, "fn", null); + __decorate([ + PropertyDecorator1, + PropertyDecorator2(80), + __param(0, ParameterDecorator1), + __param(0, ParameterDecorator2(90)) + ], Greeter.prototype, "greetings", null); + __decorate([ + PropertyDecorator1, + PropertyDecorator2(60) + ], Greeter, "x1", void 0); + Greeter = __decorate([ + ClassDecorator1, + ClassDecorator2(10), + __param(0, ParameterDecorator1), + __param(0, ParameterDecorator2(20)), + __param(1, ParameterDecorator1), + __param(1, ParameterDecorator2(30)) + ], Greeter); return Greeter; }()); -Greeter.x1 = 10; -__decorate([ - PropertyDecorator1, - PropertyDecorator2(40) -], Greeter.prototype, "greet", null); -__decorate([ - PropertyDecorator1, - PropertyDecorator2(50) -], Greeter.prototype, "x", void 0); -__decorate([ - __param(0, ParameterDecorator1), - __param(0, ParameterDecorator2(70)) -], Greeter.prototype, "fn", null); -__decorate([ - PropertyDecorator1, - PropertyDecorator2(80), - __param(0, ParameterDecorator1), - __param(0, ParameterDecorator2(90)) -], Greeter.prototype, "greetings", null); -__decorate([ - PropertyDecorator1, - PropertyDecorator2(60) -], Greeter, "x1", void 0); -Greeter = __decorate([ - ClassDecorator1, - ClassDecorator2(10), - __param(0, ParameterDecorator1), - __param(0, ParameterDecorator2(20)), - __param(1, ParameterDecorator1), - __param(1, ParameterDecorator2(30)) -], Greeter); //# sourceMappingURL=sourceMapValidationDecorators.js.map \ No newline at end of file diff --git a/tests/baselines/reference/sourceMapValidationDecorators.js.map b/tests/baselines/reference/sourceMapValidationDecorators.js.map index ac635a518f1..c5666dc3147 100644 --- a/tests/baselines/reference/sourceMapValidationDecorators.js.map +++ b/tests/baselines/reference/sourceMapValidationDecorators.js.map @@ -1,2 +1,2 @@ //// [sourceMapValidationDecorators.js.map] -{"version":3,"file":"sourceMapValidationDecorators.js","sourceRoot":"","sources":["sourceMapValidationDecorators.ts"],"names":[],"mappings":";;;;;;;;;AASA,IAAM,OAAO;IACT,iBAGS,QAAgB;QAIvB,WAAc;aAAd,UAAc,EAAd,qBAAc,EAAd,IAAc;YAAd,0BAAc;;QAJP,aAAQ,GAAR,QAAQ,CAAQ;IAKzB,CAAC;IAID,uBAAK,GAAL;QACI,MAAM,CAAC,MAAM,GAAG,IAAI,CAAC,QAAQ,GAAG,OAAO,CAAC;IAC5C,CAAC;IAUO,oBAAE,GAAV,UAGE,CAAS;QACP,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC;IACzB,CAAC;IAID,sBAAI,8BAAS;aAAb;YACI,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC;QACzB,CAAC;aAED,UAGE,SAAiB;YACf,IAAI,CAAC,QAAQ,GAAG,SAAS,CAAC;QAC9B,CAAC;;;OAPA;IAQL,cAAC;AAAD,CAAC,AA5CD,IA4CC;AArBkB,UAAE,GAAW,EAAE,CAAC;AAV/B;IAFC,kBAAkB;IAClB,kBAAkB,CAAC,EAAE,CAAC;oCAGtB;AAID;IAFC,kBAAkB;IAClB,kBAAkB,CAAC,EAAE,CAAC;kCACL;AAMlB;IACG,WAAA,mBAAmB,CAAA;IACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;iCAGzB;AAID;IAFC,kBAAkB;IAClB,kBAAkB,CAAC,EAAE,CAAC;IAMpB,WAAA,mBAAmB,CAAA;IACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;wCAJzB;AAbD;IAFC,kBAAkB;IAClB,kBAAkB,CAAC,EAAE,CAAC;yBACQ;AAvB7B,OAAO;IAFZ,eAAe;IACf,eAAe,CAAC,EAAE,CAAC;IAGb,WAAA,mBAAmB,CAAA;IACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;IAGvB,WAAA,mBAAmB,CAAA;IACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;GAPxB,OAAO,CA4CZ"} \ No newline at end of file +{"version":3,"file":"sourceMapValidationDecorators.js","sourceRoot":"","sources":["sourceMapValidationDecorators.ts"],"names":[],"mappings":";;;;;;;;;AASA;IACI,iBAGS,QAAgB;QAIvB,WAAc;aAAd,UAAc,EAAd,qBAAc,EAAd,IAAc;YAAd,0BAAc;;QAJP,aAAQ,GAAR,QAAQ,CAAQ;IAKzB,CAAC;IAID,uBAAK,GAAL;QACI,MAAM,CAAC,MAAM,GAAG,IAAI,CAAC,QAAQ,GAAG,OAAO,CAAC;IAC5C,CAAC;IAUO,oBAAE,GAAV,UAGE,CAAS;QACP,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC;IACzB,CAAC;IAID,sBAAI,8BAAS;aAAb;YACI,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC;QACzB,CAAC;aAED,UAGE,SAAiB;YACf,IAAI,CAAC,QAAQ,GAAG,SAAS,CAAC;QAC9B,CAAC;;;OAPA;IAbc,UAAE,GAAW,EAAE,CAAC;IAV/B;QAFC,kBAAkB;QAClB,kBAAkB,CAAC,EAAE,CAAC;wCAGtB;IAID;QAFC,kBAAkB;QAClB,kBAAkB,CAAC,EAAE,CAAC;sCACL;IAMlB;QACG,WAAA,mBAAmB,CAAA;QACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;qCAGzB;IAID;QAFC,kBAAkB;QAClB,kBAAkB,CAAC,EAAE,CAAC;QAMpB,WAAA,mBAAmB,CAAA;QACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;4CAJzB;IAbD;QAFC,kBAAkB;QAClB,kBAAkB,CAAC,EAAE,CAAC;6BACQ;IAvB7B,OAAO;QAFZ,eAAe;QACf,eAAe,CAAC,EAAE,CAAC;QAGb,WAAA,mBAAmB,CAAA;QACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;QAGvB,WAAA,mBAAmB,CAAA;QACnB,WAAA,mBAAmB,CAAC,EAAE,CAAC,CAAA;OAPxB,OAAO,CA4CZ;IAAD,cAAC;CAAA,AA5CD,IA4CC"} \ No newline at end of file diff --git a/tests/baselines/reference/sourceMapValidationDecorators.sourcemap.txt b/tests/baselines/reference/sourceMapValidationDecorators.sourcemap.txt index d581fdef886..2cec971546b 100644 --- a/tests/baselines/reference/sourceMapValidationDecorators.sourcemap.txt +++ b/tests/baselines/reference/sourceMapValidationDecorators.sourcemap.txt @@ -19,9 +19,7 @@ sourceFile:sourceMapValidationDecorators.ts >>>}; >>>var Greeter = (function () { 1 > -2 >^^^^ -3 > ^^^^^^^ -4 > ^^^^^^^^^^^^^^^^^^^^^^-> +2 >^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-> 1 >declare function ClassDecorator1(target: Function): void; >declare function ClassDecorator2(x: number): (target: Function) => void; >declare function PropertyDecorator1(target: Object, key: string | symbol, descriptor?: PropertyDescriptor): void; @@ -32,17 +30,13 @@ sourceFile:sourceMapValidationDecorators.ts >@ClassDecorator1 >@ClassDecorator2(10) > -2 >class -3 > Greeter 1 >Emitted(10, 1) Source(10, 1) + SourceIndex(0) -2 >Emitted(10, 5) Source(10, 7) + SourceIndex(0) -3 >Emitted(10, 12) Source(10, 14) + SourceIndex(0) --- >>> function Greeter(greeting) { 1->^^^^ 2 > ^^^^^^^^^^^^^^^^^ 3 > ^^^^^^^^ -1-> { +1->class Greeter { > 2 > constructor( > @ParameterDecorator1 @@ -362,36 +356,495 @@ sourceFile:sourceMapValidationDecorators.ts >>> configurable: true >>> }); 1->^^^^^^^ -2 > ^^^^^^^^^^^^^-> +2 > ^^^^^^^^^^^^^^-> 1-> 1->Emitted(33, 8) Source(46, 6) + SourceIndex(0) --- +>>> Greeter.x1 = 10; +1->^^^^ +2 > ^^^^^^^^^^ +3 > ^^^ +4 > ^^ +5 > ^ +1-> +2 > x1 +3 > : number = +4 > 10 +5 > ; +1->Emitted(34, 5) Source(33, 20) + SourceIndex(0) +2 >Emitted(34, 15) Source(33, 22) + SourceIndex(0) +3 >Emitted(34, 18) Source(33, 33) + SourceIndex(0) +4 >Emitted(34, 20) Source(33, 35) + SourceIndex(0) +5 >Emitted(34, 21) Source(33, 36) + SourceIndex(0) +--- +>>> __decorate([ +1 >^^^^ +2 > ^^^^^^^^^^^^^^^^^^^^^^^^-> +1 > +1 >Emitted(35, 5) Source(23, 5) + SourceIndex(0) +--- +>>> PropertyDecorator1, +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^^^^^-> +1-> +2 > PropertyDecorator1 +1->Emitted(36, 9) Source(21, 6) + SourceIndex(0) +2 >Emitted(36, 27) Source(21, 24) + SourceIndex(0) +--- +>>> PropertyDecorator2(40) +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^ +4 > ^^ +5 > ^ +6 > ^^^^^^^^^^^^-> +1-> + > @ +2 > PropertyDecorator2 +3 > ( +4 > 40 +5 > ) +1->Emitted(37, 9) Source(22, 6) + SourceIndex(0) +2 >Emitted(37, 27) Source(22, 24) + SourceIndex(0) +3 >Emitted(37, 28) Source(22, 25) + SourceIndex(0) +4 >Emitted(37, 30) Source(22, 27) + SourceIndex(0) +5 >Emitted(37, 31) Source(22, 28) + SourceIndex(0) +--- +>>> ], Greeter.prototype, "greet", null); +1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +1-> + > greet() { + > return "

" + this.greeting + "

"; + > } +1->Emitted(38, 41) Source(25, 6) + SourceIndex(0) +--- +>>> __decorate([ +1 >^^^^ +2 > ^^^^^^^^^^^^^^^^^^^^^^^^-> +1 > + > + > @PropertyDecorator1 + > @PropertyDecorator2(50) + > +1 >Emitted(39, 5) Source(29, 5) + SourceIndex(0) +--- +>>> PropertyDecorator1, +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^^^^^-> +1-> +2 > PropertyDecorator1 +1->Emitted(40, 9) Source(27, 6) + SourceIndex(0) +2 >Emitted(40, 27) Source(27, 24) + SourceIndex(0) +--- +>>> PropertyDecorator2(50) +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^ +4 > ^^ +5 > ^ +6 > ^^^^^^^^^^-> +1-> + > @ +2 > PropertyDecorator2 +3 > ( +4 > 50 +5 > ) +1->Emitted(41, 9) Source(28, 6) + SourceIndex(0) +2 >Emitted(41, 27) Source(28, 24) + SourceIndex(0) +3 >Emitted(41, 28) Source(28, 25) + SourceIndex(0) +4 >Emitted(41, 30) Source(28, 27) + SourceIndex(0) +5 >Emitted(41, 31) Source(28, 28) + SourceIndex(0) +--- +>>> ], Greeter.prototype, "x", void 0); +1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +1-> + > private x: string; +1->Emitted(42, 39) Source(29, 23) + SourceIndex(0) +--- +>>> __decorate([ +1 >^^^^ +2 > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-> +1 > + > + > @PropertyDecorator1 + > @PropertyDecorator2(60) + > private static x1: number = 10; + > + > +1 >Emitted(43, 5) Source(35, 5) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator1), +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^^^^-> +1->private fn( + > @ +2 > +3 > ParameterDecorator1 +4 > +1->Emitted(44, 9) Source(36, 8) + SourceIndex(0) +2 >Emitted(44, 20) Source(36, 8) + SourceIndex(0) +3 >Emitted(44, 39) Source(36, 27) + SourceIndex(0) +4 >Emitted(44, 40) Source(36, 27) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator2(70)) +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^ +6 > ^ +7 > ^ +1-> + > @ +2 > +3 > ParameterDecorator2 +4 > ( +5 > 70 +6 > ) +7 > +1->Emitted(45, 9) Source(37, 8) + SourceIndex(0) +2 >Emitted(45, 20) Source(37, 8) + SourceIndex(0) +3 >Emitted(45, 39) Source(37, 27) + SourceIndex(0) +4 >Emitted(45, 40) Source(37, 28) + SourceIndex(0) +5 >Emitted(45, 42) Source(37, 30) + SourceIndex(0) +6 >Emitted(45, 43) Source(37, 31) + SourceIndex(0) +7 >Emitted(45, 44) Source(37, 31) + SourceIndex(0) +--- +>>> ], Greeter.prototype, "fn", null); +1 >^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +1 > + > x: number) { + > return this.greeting; + > } +1 >Emitted(46, 38) Source(40, 6) + SourceIndex(0) +--- +>>> __decorate([ +1 >^^^^ +2 > ^^^^^^^^^^^^^^^^^^^^^^^^-> +1 > + > + > @PropertyDecorator1 + > @PropertyDecorator2(80) + > +1 >Emitted(47, 5) Source(44, 5) + SourceIndex(0) +--- +>>> PropertyDecorator1, +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^^^^^^-> +1-> +2 > PropertyDecorator1 +1->Emitted(48, 9) Source(42, 6) + SourceIndex(0) +2 >Emitted(48, 27) Source(42, 24) + SourceIndex(0) +--- +>>> PropertyDecorator2(80), +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^ +4 > ^^ +5 > ^ +6 > ^^^^^^^^^^^-> +1-> + > @ +2 > PropertyDecorator2 +3 > ( +4 > 80 +5 > ) +1->Emitted(49, 9) Source(43, 6) + SourceIndex(0) +2 >Emitted(49, 27) Source(43, 24) + SourceIndex(0) +3 >Emitted(49, 28) Source(43, 25) + SourceIndex(0) +4 >Emitted(49, 30) Source(43, 27) + SourceIndex(0) +5 >Emitted(49, 31) Source(43, 28) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator1), +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^^^^-> +1-> + > get greetings() { + > return this.greeting; + > } + > + > set greetings( + > @ +2 > +3 > ParameterDecorator1 +4 > +1->Emitted(50, 9) Source(49, 8) + SourceIndex(0) +2 >Emitted(50, 20) Source(49, 8) + SourceIndex(0) +3 >Emitted(50, 39) Source(49, 27) + SourceIndex(0) +4 >Emitted(50, 40) Source(49, 27) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator2(90)) +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^ +6 > ^ +7 > ^ +8 > ^^^-> +1-> + > @ +2 > +3 > ParameterDecorator2 +4 > ( +5 > 90 +6 > ) +7 > +1->Emitted(51, 9) Source(50, 8) + SourceIndex(0) +2 >Emitted(51, 20) Source(50, 8) + SourceIndex(0) +3 >Emitted(51, 39) Source(50, 27) + SourceIndex(0) +4 >Emitted(51, 40) Source(50, 28) + SourceIndex(0) +5 >Emitted(51, 42) Source(50, 30) + SourceIndex(0) +6 >Emitted(51, 43) Source(50, 31) + SourceIndex(0) +7 >Emitted(51, 44) Source(50, 31) + SourceIndex(0) +--- +>>> ], Greeter.prototype, "greetings", null); +1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +1-> +1->Emitted(52, 45) Source(46, 6) + SourceIndex(0) +--- +>>> __decorate([ +1 >^^^^ +2 > ^^^^^^^^^^^^^^^^^^^^^^^^-> +1 > +1 >Emitted(53, 5) Source(33, 5) + SourceIndex(0) +--- +>>> PropertyDecorator1, +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^^^^^-> +1-> +2 > PropertyDecorator1 +1->Emitted(54, 9) Source(31, 6) + SourceIndex(0) +2 >Emitted(54, 27) Source(31, 24) + SourceIndex(0) +--- +>>> PropertyDecorator2(60) +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^^^^ +3 > ^ +4 > ^^ +5 > ^ +6 > ^-> +1-> + > @ +2 > PropertyDecorator2 +3 > ( +4 > 60 +5 > ) +1->Emitted(55, 9) Source(32, 6) + SourceIndex(0) +2 >Emitted(55, 27) Source(32, 24) + SourceIndex(0) +3 >Emitted(55, 28) Source(32, 25) + SourceIndex(0) +4 >Emitted(55, 30) Source(32, 27) + SourceIndex(0) +5 >Emitted(55, 31) Source(32, 28) + SourceIndex(0) +--- +>>> ], Greeter, "x1", void 0); +1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +1-> + > private static x1: number = 10; +1->Emitted(56, 30) Source(33, 36) + SourceIndex(0) +--- +>>> Greeter = __decorate([ +1 >^^^^ +2 > ^^^^^^^ +3 > ^^^^^^^^^^^^^^-> +1 > +2 > Greeter +1 >Emitted(57, 5) Source(10, 7) + SourceIndex(0) +2 >Emitted(57, 12) Source(10, 14) + SourceIndex(0) +--- +>>> ClassDecorator1, +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^ +3 > ^^^^^^-> +1-> +2 > ClassDecorator1 +1->Emitted(58, 9) Source(8, 2) + SourceIndex(0) +2 >Emitted(58, 24) Source(8, 17) + SourceIndex(0) +--- +>>> ClassDecorator2(10), +1->^^^^^^^^ +2 > ^^^^^^^^^^^^^^^ +3 > ^ +4 > ^^ +5 > ^ +6 > ^^^^^^^^^^^^^^-> +1-> + >@ +2 > ClassDecorator2 +3 > ( +4 > 10 +5 > ) +1->Emitted(59, 9) Source(9, 2) + SourceIndex(0) +2 >Emitted(59, 24) Source(9, 17) + SourceIndex(0) +3 >Emitted(59, 25) Source(9, 18) + SourceIndex(0) +4 >Emitted(59, 27) Source(9, 20) + SourceIndex(0) +5 >Emitted(59, 28) Source(9, 21) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator1), +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^^^^^-> +1-> + >class Greeter { + > constructor( + > @ +2 > +3 > ParameterDecorator1 +4 > +1->Emitted(60, 9) Source(12, 8) + SourceIndex(0) +2 >Emitted(60, 20) Source(12, 8) + SourceIndex(0) +3 >Emitted(60, 39) Source(12, 27) + SourceIndex(0) +4 >Emitted(60, 40) Source(12, 27) + SourceIndex(0) +--- +>>> __param(0, ParameterDecorator2(20)), +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^ +6 > ^ +7 > ^ +1-> + > @ +2 > +3 > ParameterDecorator2 +4 > ( +5 > 20 +6 > ) +7 > +1->Emitted(61, 9) Source(13, 8) + SourceIndex(0) +2 >Emitted(61, 20) Source(13, 8) + SourceIndex(0) +3 >Emitted(61, 39) Source(13, 27) + SourceIndex(0) +4 >Emitted(61, 40) Source(13, 28) + SourceIndex(0) +5 >Emitted(61, 42) Source(13, 30) + SourceIndex(0) +6 >Emitted(61, 43) Source(13, 31) + SourceIndex(0) +7 >Emitted(61, 44) Source(13, 31) + SourceIndex(0) +--- +>>> __param(1, ParameterDecorator1), +1 >^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^^^^-> +1 > + > public greeting: string, + > + > @ +2 > +3 > ParameterDecorator1 +4 > +1 >Emitted(62, 9) Source(16, 8) + SourceIndex(0) +2 >Emitted(62, 20) Source(16, 8) + SourceIndex(0) +3 >Emitted(62, 39) Source(16, 27) + SourceIndex(0) +4 >Emitted(62, 40) Source(16, 27) + SourceIndex(0) +--- +>>> __param(1, ParameterDecorator2(30)) +1->^^^^^^^^ +2 > ^^^^^^^^^^^ +3 > ^^^^^^^^^^^^^^^^^^^ +4 > ^ +5 > ^^ +6 > ^ +7 > ^ +1-> + > @ +2 > +3 > ParameterDecorator2 +4 > ( +5 > 30 +6 > ) +7 > +1->Emitted(63, 9) Source(17, 8) + SourceIndex(0) +2 >Emitted(63, 20) Source(17, 8) + SourceIndex(0) +3 >Emitted(63, 39) Source(17, 27) + SourceIndex(0) +4 >Emitted(63, 40) Source(17, 28) + SourceIndex(0) +5 >Emitted(63, 42) Source(17, 30) + SourceIndex(0) +6 >Emitted(63, 43) Source(17, 31) + SourceIndex(0) +7 >Emitted(63, 44) Source(17, 31) + SourceIndex(0) +--- +>>> ], Greeter); +1 >^^^^^^^ +2 > ^^^^^^^ +3 > ^ +4 > ^^^^^-> +1 > +2 > Greeter +3 > { + > constructor( + > @ParameterDecorator1 + > @ParameterDecorator2(20) + > public greeting: string, + > + > @ParameterDecorator1 + > @ParameterDecorator2(30) + > ...b: string[]) { + > } + > + > @PropertyDecorator1 + > @PropertyDecorator2(40) + > greet() { + > return "

" + this.greeting + "

"; + > } + > + > @PropertyDecorator1 + > @PropertyDecorator2(50) + > private x: string; + > + > @PropertyDecorator1 + > @PropertyDecorator2(60) + > private static x1: number = 10; + > + > private fn( + > @ParameterDecorator1 + > @ParameterDecorator2(70) + > x: number) { + > return this.greeting; + > } + > + > @PropertyDecorator1 + > @PropertyDecorator2(80) + > get greetings() { + > return this.greeting; + > } + > + > set greetings( + > @ParameterDecorator1 + > @ParameterDecorator2(90) + > greetings: string) { + > this.greeting = greetings; + > } + > } +1 >Emitted(64, 8) Source(10, 7) + SourceIndex(0) +2 >Emitted(64, 15) Source(10, 14) + SourceIndex(0) +3 >Emitted(64, 16) Source(54, 2) + SourceIndex(0) +--- >>> return Greeter; 1->^^^^ 2 > ^^^^^^^^^^^^^^ -1-> - > - > set greetings( - > @ParameterDecorator1 - > @ParameterDecorator2(90) - > greetings: string) { - > this.greeting = greetings; - > } - > +1-> 2 > } -1->Emitted(34, 5) Source(54, 1) + SourceIndex(0) -2 >Emitted(34, 19) Source(54, 2) + SourceIndex(0) +1->Emitted(65, 5) Source(54, 1) + SourceIndex(0) +2 >Emitted(65, 19) Source(54, 2) + SourceIndex(0) --- >>>}()); +1 >^ +2 > +3 > ^^^^ +4 > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-> 1 > -2 >^ -3 > -4 > ^^^^ -5 > ^^^^^^^^^^^^-> -1 > -2 >} -3 > -4 > class Greeter { +2 > +3 > class Greeter { > constructor( > @ParameterDecorator1 > @ParameterDecorator2(20) @@ -436,478 +889,8 @@ sourceFile:sourceMapValidationDecorators.ts > this.greeting = greetings; > } > } -1 >Emitted(35, 1) Source(54, 1) + SourceIndex(0) -2 >Emitted(35, 2) Source(54, 2) + SourceIndex(0) -3 >Emitted(35, 2) Source(10, 1) + SourceIndex(0) -4 >Emitted(35, 6) Source(54, 2) + SourceIndex(0) ---- ->>>Greeter.x1 = 10; -1-> -2 >^^^^^^^^^^ -3 > ^^^ -4 > ^^ -5 > ^ -1-> -2 >x1 -3 > : number = -4 > 10 -5 > ; -1->Emitted(36, 1) Source(33, 20) + SourceIndex(0) -2 >Emitted(36, 11) Source(33, 22) + SourceIndex(0) -3 >Emitted(36, 14) Source(33, 33) + SourceIndex(0) -4 >Emitted(36, 16) Source(33, 35) + SourceIndex(0) -5 >Emitted(36, 17) Source(33, 36) + SourceIndex(0) ---- ->>>__decorate([ -1 > -2 >^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > -1 >Emitted(37, 1) Source(23, 5) + SourceIndex(0) ---- ->>> PropertyDecorator1, -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^^^^^-> -1-> -2 > PropertyDecorator1 -1->Emitted(38, 5) Source(21, 6) + SourceIndex(0) -2 >Emitted(38, 23) Source(21, 24) + SourceIndex(0) ---- ->>> PropertyDecorator2(40) -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^ -4 > ^^ -5 > ^ -6 > ^^^^^^^^^^^^-> -1-> - > @ -2 > PropertyDecorator2 -3 > ( -4 > 40 -5 > ) -1->Emitted(39, 5) Source(22, 6) + SourceIndex(0) -2 >Emitted(39, 23) Source(22, 24) + SourceIndex(0) -3 >Emitted(39, 24) Source(22, 25) + SourceIndex(0) -4 >Emitted(39, 26) Source(22, 27) + SourceIndex(0) -5 >Emitted(39, 27) Source(22, 28) + SourceIndex(0) ---- ->>>], Greeter.prototype, "greet", null); -1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -1-> - > greet() { - > return "

" + this.greeting + "

"; - > } -1->Emitted(40, 37) Source(25, 6) + SourceIndex(0) ---- ->>>__decorate([ -1 > -2 >^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > - > - > @PropertyDecorator1 - > @PropertyDecorator2(50) - > -1 >Emitted(41, 1) Source(29, 5) + SourceIndex(0) ---- ->>> PropertyDecorator1, -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^^^^^-> -1-> -2 > PropertyDecorator1 -1->Emitted(42, 5) Source(27, 6) + SourceIndex(0) -2 >Emitted(42, 23) Source(27, 24) + SourceIndex(0) ---- ->>> PropertyDecorator2(50) -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^ -4 > ^^ -5 > ^ -6 > ^^^^^^^^^^-> -1-> - > @ -2 > PropertyDecorator2 -3 > ( -4 > 50 -5 > ) -1->Emitted(43, 5) Source(28, 6) + SourceIndex(0) -2 >Emitted(43, 23) Source(28, 24) + SourceIndex(0) -3 >Emitted(43, 24) Source(28, 25) + SourceIndex(0) -4 >Emitted(43, 26) Source(28, 27) + SourceIndex(0) -5 >Emitted(43, 27) Source(28, 28) + SourceIndex(0) ---- ->>>], Greeter.prototype, "x", void 0); -1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -1-> - > private x: string; -1->Emitted(44, 35) Source(29, 23) + SourceIndex(0) ---- ->>>__decorate([ -1 > -2 >^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > - > - > @PropertyDecorator1 - > @PropertyDecorator2(60) - > private static x1: number = 10; - > - > -1 >Emitted(45, 1) Source(35, 5) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator1), -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^^^^-> -1->private fn( - > @ -2 > -3 > ParameterDecorator1 -4 > -1->Emitted(46, 5) Source(36, 8) + SourceIndex(0) -2 >Emitted(46, 16) Source(36, 8) + SourceIndex(0) -3 >Emitted(46, 35) Source(36, 27) + SourceIndex(0) -4 >Emitted(46, 36) Source(36, 27) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator2(70)) -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^ -6 > ^ -7 > ^ -1-> - > @ -2 > -3 > ParameterDecorator2 -4 > ( -5 > 70 -6 > ) -7 > -1->Emitted(47, 5) Source(37, 8) + SourceIndex(0) -2 >Emitted(47, 16) Source(37, 8) + SourceIndex(0) -3 >Emitted(47, 35) Source(37, 27) + SourceIndex(0) -4 >Emitted(47, 36) Source(37, 28) + SourceIndex(0) -5 >Emitted(47, 38) Source(37, 30) + SourceIndex(0) -6 >Emitted(47, 39) Source(37, 31) + SourceIndex(0) -7 >Emitted(47, 40) Source(37, 31) + SourceIndex(0) ---- ->>>], Greeter.prototype, "fn", null); -1 >^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -1 > - > x: number) { - > return this.greeting; - > } -1 >Emitted(48, 34) Source(40, 6) + SourceIndex(0) ---- ->>>__decorate([ -1 > -2 >^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > - > - > @PropertyDecorator1 - > @PropertyDecorator2(80) - > -1 >Emitted(49, 1) Source(44, 5) + SourceIndex(0) ---- ->>> PropertyDecorator1, -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^^^^^^-> -1-> -2 > PropertyDecorator1 -1->Emitted(50, 5) Source(42, 6) + SourceIndex(0) -2 >Emitted(50, 23) Source(42, 24) + SourceIndex(0) ---- ->>> PropertyDecorator2(80), -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^ -4 > ^^ -5 > ^ -6 > ^^^^^^^^^^^-> -1-> - > @ -2 > PropertyDecorator2 -3 > ( -4 > 80 -5 > ) -1->Emitted(51, 5) Source(43, 6) + SourceIndex(0) -2 >Emitted(51, 23) Source(43, 24) + SourceIndex(0) -3 >Emitted(51, 24) Source(43, 25) + SourceIndex(0) -4 >Emitted(51, 26) Source(43, 27) + SourceIndex(0) -5 >Emitted(51, 27) Source(43, 28) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator1), -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^^^^-> -1-> - > get greetings() { - > return this.greeting; - > } - > - > set greetings( - > @ -2 > -3 > ParameterDecorator1 -4 > -1->Emitted(52, 5) Source(49, 8) + SourceIndex(0) -2 >Emitted(52, 16) Source(49, 8) + SourceIndex(0) -3 >Emitted(52, 35) Source(49, 27) + SourceIndex(0) -4 >Emitted(52, 36) Source(49, 27) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator2(90)) -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^ -6 > ^ -7 > ^ -8 > ^^^-> -1-> - > @ -2 > -3 > ParameterDecorator2 -4 > ( -5 > 90 -6 > ) -7 > -1->Emitted(53, 5) Source(50, 8) + SourceIndex(0) -2 >Emitted(53, 16) Source(50, 8) + SourceIndex(0) -3 >Emitted(53, 35) Source(50, 27) + SourceIndex(0) -4 >Emitted(53, 36) Source(50, 28) + SourceIndex(0) -5 >Emitted(53, 38) Source(50, 30) + SourceIndex(0) -6 >Emitted(53, 39) Source(50, 31) + SourceIndex(0) -7 >Emitted(53, 40) Source(50, 31) + SourceIndex(0) ---- ->>>], Greeter.prototype, "greetings", null); -1->^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -1-> -1->Emitted(54, 41) Source(46, 6) + SourceIndex(0) ---- ->>>__decorate([ -1 > -2 >^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > -1 >Emitted(55, 1) Source(33, 5) + SourceIndex(0) ---- ->>> PropertyDecorator1, -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^^^^^-> -1-> -2 > PropertyDecorator1 -1->Emitted(56, 5) Source(31, 6) + SourceIndex(0) -2 >Emitted(56, 23) Source(31, 24) + SourceIndex(0) ---- ->>> PropertyDecorator2(60) -1->^^^^ -2 > ^^^^^^^^^^^^^^^^^^ -3 > ^ -4 > ^^ -5 > ^ -6 > ^-> -1-> - > @ -2 > PropertyDecorator2 -3 > ( -4 > 60 -5 > ) -1->Emitted(57, 5) Source(32, 6) + SourceIndex(0) -2 >Emitted(57, 23) Source(32, 24) + SourceIndex(0) -3 >Emitted(57, 24) Source(32, 25) + SourceIndex(0) -4 >Emitted(57, 26) Source(32, 27) + SourceIndex(0) -5 >Emitted(57, 27) Source(32, 28) + SourceIndex(0) ---- ->>>], Greeter, "x1", void 0); -1->^^^^^^^^^^^^^^^^^^^^^^^^^ -1-> - > private static x1: number = 10; -1->Emitted(58, 26) Source(33, 36) + SourceIndex(0) ---- ->>>Greeter = __decorate([ -1 > -2 >^^^^^^^ -3 > ^^^^^^^^^^^^^^-> -1 > -2 >Greeter -1 >Emitted(59, 1) Source(10, 7) + SourceIndex(0) -2 >Emitted(59, 8) Source(10, 14) + SourceIndex(0) ---- ->>> ClassDecorator1, -1->^^^^ -2 > ^^^^^^^^^^^^^^^ -3 > ^^^^^^-> -1-> -2 > ClassDecorator1 -1->Emitted(60, 5) Source(8, 2) + SourceIndex(0) -2 >Emitted(60, 20) Source(8, 17) + SourceIndex(0) ---- ->>> ClassDecorator2(10), -1->^^^^ -2 > ^^^^^^^^^^^^^^^ -3 > ^ -4 > ^^ -5 > ^ -6 > ^^^^^^^^^^^^^^-> -1-> - >@ -2 > ClassDecorator2 -3 > ( -4 > 10 -5 > ) -1->Emitted(61, 5) Source(9, 2) + SourceIndex(0) -2 >Emitted(61, 20) Source(9, 17) + SourceIndex(0) -3 >Emitted(61, 21) Source(9, 18) + SourceIndex(0) -4 >Emitted(61, 23) Source(9, 20) + SourceIndex(0) -5 >Emitted(61, 24) Source(9, 21) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator1), -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^^^^^-> -1-> - >class Greeter { - > constructor( - > @ -2 > -3 > ParameterDecorator1 -4 > -1->Emitted(62, 5) Source(12, 8) + SourceIndex(0) -2 >Emitted(62, 16) Source(12, 8) + SourceIndex(0) -3 >Emitted(62, 35) Source(12, 27) + SourceIndex(0) -4 >Emitted(62, 36) Source(12, 27) + SourceIndex(0) ---- ->>> __param(0, ParameterDecorator2(20)), -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^ -6 > ^ -7 > ^ -1-> - > @ -2 > -3 > ParameterDecorator2 -4 > ( -5 > 20 -6 > ) -7 > -1->Emitted(63, 5) Source(13, 8) + SourceIndex(0) -2 >Emitted(63, 16) Source(13, 8) + SourceIndex(0) -3 >Emitted(63, 35) Source(13, 27) + SourceIndex(0) -4 >Emitted(63, 36) Source(13, 28) + SourceIndex(0) -5 >Emitted(63, 38) Source(13, 30) + SourceIndex(0) -6 >Emitted(63, 39) Source(13, 31) + SourceIndex(0) -7 >Emitted(63, 40) Source(13, 31) + SourceIndex(0) ---- ->>> __param(1, ParameterDecorator1), -1 >^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^^^^-> -1 > - > public greeting: string, - > - > @ -2 > -3 > ParameterDecorator1 -4 > -1 >Emitted(64, 5) Source(16, 8) + SourceIndex(0) -2 >Emitted(64, 16) Source(16, 8) + SourceIndex(0) -3 >Emitted(64, 35) Source(16, 27) + SourceIndex(0) -4 >Emitted(64, 36) Source(16, 27) + SourceIndex(0) ---- ->>> __param(1, ParameterDecorator2(30)) -1->^^^^ -2 > ^^^^^^^^^^^ -3 > ^^^^^^^^^^^^^^^^^^^ -4 > ^ -5 > ^^ -6 > ^ -7 > ^ -1-> - > @ -2 > -3 > ParameterDecorator2 -4 > ( -5 > 30 -6 > ) -7 > -1->Emitted(65, 5) Source(17, 8) + SourceIndex(0) -2 >Emitted(65, 16) Source(17, 8) + SourceIndex(0) -3 >Emitted(65, 35) Source(17, 27) + SourceIndex(0) -4 >Emitted(65, 36) Source(17, 28) + SourceIndex(0) -5 >Emitted(65, 38) Source(17, 30) + SourceIndex(0) -6 >Emitted(65, 39) Source(17, 31) + SourceIndex(0) -7 >Emitted(65, 40) Source(17, 31) + SourceIndex(0) ---- ->>>], Greeter); -1 >^^^ -2 > ^^^^^^^ -3 > ^ -4 > ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^-> -1 > -2 > Greeter -3 > { - > constructor( - > @ParameterDecorator1 - > @ParameterDecorator2(20) - > public greeting: string, - > - > @ParameterDecorator1 - > @ParameterDecorator2(30) - > ...b: string[]) { - > } - > - > @PropertyDecorator1 - > @PropertyDecorator2(40) - > greet() { - > return "

" + this.greeting + "

"; - > } - > - > @PropertyDecorator1 - > @PropertyDecorator2(50) - > private x: string; - > - > @PropertyDecorator1 - > @PropertyDecorator2(60) - > private static x1: number = 10; - > - > private fn( - > @ParameterDecorator1 - > @ParameterDecorator2(70) - > x: number) { - > return this.greeting; - > } - > - > @PropertyDecorator1 - > @PropertyDecorator2(80) - > get greetings() { - > return this.greeting; - > } - > - > set greetings( - > @ParameterDecorator1 - > @ParameterDecorator2(90) - > greetings: string) { - > this.greeting = greetings; - > } - > } -1 >Emitted(66, 4) Source(10, 7) + SourceIndex(0) -2 >Emitted(66, 11) Source(10, 14) + SourceIndex(0) -3 >Emitted(66, 12) Source(54, 2) + SourceIndex(0) +1 >Emitted(66, 2) Source(54, 2) + SourceIndex(0) +2 >Emitted(66, 2) Source(10, 1) + SourceIndex(0) +3 >Emitted(66, 6) Source(54, 2) + SourceIndex(0) --- >>>//# sourceMappingURL=sourceMapValidationDecorators.js.map \ No newline at end of file diff --git a/tests/baselines/reference/staticAnonymousTypeNotReferencingTypeParameter.js b/tests/baselines/reference/staticAnonymousTypeNotReferencingTypeParameter.js index a641ecd6f03..62a23d538c4 100644 --- a/tests/baselines/reference/staticAnonymousTypeNotReferencingTypeParameter.js +++ b/tests/baselines/reference/staticAnonymousTypeNotReferencingTypeParameter.js @@ -148,9 +148,9 @@ function outer(x) { var Inner = (function () { function Inner() { } + Inner.y = x; return Inner; }()); - Inner.y = x; return Inner; } var y = outer(5).y; diff --git a/tests/baselines/reference/staticClassProps.js b/tests/baselines/reference/staticClassProps.js index 48798bd4def..31aa67c56df 100644 --- a/tests/baselines/reference/staticClassProps.js +++ b/tests/baselines/reference/staticClassProps.js @@ -14,6 +14,6 @@ var C = (function () { } C.prototype.foo = function () { }; + C.z = 1; return C; }()); -C.z = 1; diff --git a/tests/baselines/reference/staticMemberAccessOffDerivedType1.js b/tests/baselines/reference/staticMemberAccessOffDerivedType1.js index 41f2da7f4af..684594ffd5c 100644 --- a/tests/baselines/reference/staticMemberAccessOffDerivedType1.js +++ b/tests/baselines/reference/staticMemberAccessOffDerivedType1.js @@ -33,6 +33,6 @@ var P = (function (_super) { function P() { return _super !== null && _super.apply(this, arguments) || this; } + P.SomeNumber = P.GetNumber(); return P; }(SomeBase)); -P.SomeNumber = P.GetNumber(); diff --git a/tests/baselines/reference/staticMemberInitialization.js b/tests/baselines/reference/staticMemberInitialization.js index 13a5c8c25c6..c21c29ed4f8 100644 --- a/tests/baselines/reference/staticMemberInitialization.js +++ b/tests/baselines/reference/staticMemberInitialization.js @@ -10,8 +10,8 @@ var r = C.x; var C = (function () { function C() { } + C.x = 1; return C; }()); -C.x = 1; var c = new C(); var r = C.x; diff --git a/tests/baselines/reference/staticMemberWithStringAndNumberNames.js b/tests/baselines/reference/staticMemberWithStringAndNumberNames.js index 9d8846ba963..2fdd64ea04b 100644 --- a/tests/baselines/reference/staticMemberWithStringAndNumberNames.js +++ b/tests/baselines/reference/staticMemberWithStringAndNumberNames.js @@ -19,10 +19,10 @@ var C = (function () { this.x2 = C['0']; this.x3 = C[0]; } + C["foo"] = 0; + C[0] = 1; + C.s = C['foo']; + C.s2 = C['0']; + C.s3 = C[0]; return C; }()); -C["foo"] = 0; -C[0] = 1; -C.s = C['foo']; -C.s2 = C['0']; -C.s3 = C[0]; diff --git a/tests/baselines/reference/staticModifierAlreadySeen.js b/tests/baselines/reference/staticModifierAlreadySeen.js index c37d4c0807a..76f8b050d6f 100644 --- a/tests/baselines/reference/staticModifierAlreadySeen.js +++ b/tests/baselines/reference/staticModifierAlreadySeen.js @@ -9,6 +9,6 @@ var C = (function () { function C() { } C.bar = function () { }; + C.foo = 1; return C; }()); -C.foo = 1; diff --git a/tests/baselines/reference/staticPropSuper.js b/tests/baselines/reference/staticPropSuper.js index 5c22232534f..dc308a4769e 100644 --- a/tests/baselines/reference/staticPropSuper.js +++ b/tests/baselines/reference/staticPropSuper.js @@ -59,9 +59,9 @@ var B = (function (_super) { _this = _super.call(this) || this; return _this; } + B.s = 9; return B; }(A)); -B.s = 9; var C = (function (_super) { __extends(C, _super); function C() { diff --git a/tests/baselines/reference/statics.js b/tests/baselines/reference/statics.js index d52a28208e6..3776c09c8ce 100644 --- a/tests/baselines/reference/statics.js +++ b/tests/baselines/reference/statics.js @@ -45,11 +45,11 @@ var M; C.f = function (n) { return "wow: " + (n + C.y + C.pub + C.priv); }; + C.priv = 2; + C.pub = 3; + C.y = C.priv; return C; }()); - C.priv = 2; - C.pub = 3; - C.y = C.priv; M.C = C; var c = C.y; function f() { diff --git a/tests/baselines/reference/staticsInConstructorBodies.js b/tests/baselines/reference/staticsInConstructorBodies.js index edd49456ef7..9bc3ed29325 100644 --- a/tests/baselines/reference/staticsInConstructorBodies.js +++ b/tests/baselines/reference/staticsInConstructorBodies.js @@ -11,6 +11,6 @@ var C = (function () { function C() { } C.m1 = function () { }; // ERROR + C.p1 = 0; // ERROR return C; }()); -C.p1 = 0; // ERROR diff --git a/tests/baselines/reference/staticsNotInScopeInClodule.js b/tests/baselines/reference/staticsNotInScopeInClodule.js index ccaace996cd..c43e22fce4c 100644 --- a/tests/baselines/reference/staticsNotInScopeInClodule.js +++ b/tests/baselines/reference/staticsNotInScopeInClodule.js @@ -11,9 +11,9 @@ module Clod { var Clod = (function () { function Clod() { } + Clod.x = 10; return Clod; }()); -Clod.x = 10; (function (Clod) { var p = x; // x isn't in scope here })(Clod || (Clod = {})); diff --git a/tests/baselines/reference/strictModeInConstructor.js b/tests/baselines/reference/strictModeInConstructor.js index 65426391967..eb2286556ac 100644 --- a/tests/baselines/reference/strictModeInConstructor.js +++ b/tests/baselines/reference/strictModeInConstructor.js @@ -114,9 +114,9 @@ var Bs = (function (_super) { "use strict"; // No error return _super.call(this) || this; } + Bs.s = 9; return Bs; }(A)); -Bs.s = 9; var Cs = (function (_super) { __extends(Cs, _super); function Cs() { @@ -124,9 +124,9 @@ var Cs = (function (_super) { "use strict"; return _this; } + Cs.s = 9; return Cs; }(A)); -Cs.s = 9; var Ds = (function (_super) { __extends(Ds, _super); function Ds() { @@ -136,6 +136,6 @@ var Ds = (function (_super) { "use strict"; return _this; } + Ds.s = 9; return Ds; }(A)); -Ds.s = 9; diff --git a/tests/baselines/reference/superAccess.js b/tests/baselines/reference/superAccess.js index 468e2155e48..aac00259613 100644 --- a/tests/baselines/reference/superAccess.js +++ b/tests/baselines/reference/superAccess.js @@ -29,9 +29,9 @@ var MyBase = (function () { this.S2 = "test"; this.f = function () { return 5; }; } + MyBase.S1 = 5; return MyBase; }()); -MyBase.S1 = 5; var MyDerived = (function (_super) { __extends(MyDerived, _super); function MyDerived() { diff --git a/tests/baselines/reference/superAccess2.js b/tests/baselines/reference/superAccess2.js index 51e8f61ab28..9fa848dbf6a 100644 --- a/tests/baselines/reference/superAccess2.js +++ b/tests/baselines/reference/superAccess2.js @@ -64,6 +64,6 @@ var Q = (function (_super) { _super.x.call(this); // error _super.y.call(this); }; + Q.yy = _super.; // error for static initializer accessing super return Q; }(P)); -Q.yy = _super.; // error for static initializer accessing super diff --git a/tests/baselines/reference/thisInArrowFunctionInStaticInitializer1.js b/tests/baselines/reference/thisInArrowFunctionInStaticInitializer1.js index 03b86b1d225..88a4f5c6e5c 100644 --- a/tests/baselines/reference/thisInArrowFunctionInStaticInitializer1.js +++ b/tests/baselines/reference/thisInArrowFunctionInStaticInitializer1.js @@ -9,14 +9,13 @@ class Vector { } //// [thisInArrowFunctionInStaticInitializer1.js] -var _this = this; function log(a) { } var Vector = (function () { function Vector() { } + Vector.foo = function () { + // 'this' should not be available in a static initializer. + log(_this); + }; return Vector; }()); -Vector.foo = function () { - // 'this' should not be available in a static initializer. - log(_this); -}; diff --git a/tests/baselines/reference/thisInConstructorParameter2.js b/tests/baselines/reference/thisInConstructorParameter2.js index ba2917c5a4e..7260ecafcb9 100644 --- a/tests/baselines/reference/thisInConstructorParameter2.js +++ b/tests/baselines/reference/thisInConstructorParameter2.js @@ -25,6 +25,6 @@ var P = (function () { if (zz === void 0) { zz = this; } zz.y; }; + P.y = this; return P; }()); -P.y = this; diff --git a/tests/baselines/reference/thisInInvalidContexts.js b/tests/baselines/reference/thisInInvalidContexts.js index 25350fb78cf..24b25d46a34 100644 --- a/tests/baselines/reference/thisInInvalidContexts.js +++ b/tests/baselines/reference/thisInInvalidContexts.js @@ -63,9 +63,9 @@ var __extends = (this && this.__extends) || (function () { var ErrClass1 = (function () { function ErrClass1() { } + ErrClass1.t = this; // Error return ErrClass1; }()); -ErrClass1.t = this; // Error var BaseErrClass = (function () { function BaseErrClass(t) { } diff --git a/tests/baselines/reference/thisInInvalidContextsExternalModule.js b/tests/baselines/reference/thisInInvalidContextsExternalModule.js index 070d5597fcc..845183d8df5 100644 --- a/tests/baselines/reference/thisInInvalidContextsExternalModule.js +++ b/tests/baselines/reference/thisInInvalidContextsExternalModule.js @@ -64,9 +64,9 @@ var __extends = (this && this.__extends) || (function () { var ErrClass1 = (function () { function ErrClass1() { } + ErrClass1.t = this; // Error return ErrClass1; }()); -ErrClass1.t = this; // Error var BaseErrClass = (function () { function BaseErrClass(t) { } diff --git a/tests/baselines/reference/thisInOuterClassBody.js b/tests/baselines/reference/thisInOuterClassBody.js index 40b0e2b78ae..40e4a2e2485 100644 --- a/tests/baselines/reference/thisInOuterClassBody.js +++ b/tests/baselines/reference/thisInOuterClassBody.js @@ -36,6 +36,6 @@ var Foo = (function () { var a = this.y; var b = this.x; }; + Foo.y = this; return Foo; }()); -Foo.y = this; diff --git a/tests/baselines/reference/thisInPropertyBoundDeclarations.js b/tests/baselines/reference/thisInPropertyBoundDeclarations.js index f5967fbb5b2..0b378cec51a 100644 --- a/tests/baselines/reference/thisInPropertyBoundDeclarations.js +++ b/tests/baselines/reference/thisInPropertyBoundDeclarations.js @@ -74,13 +74,13 @@ var Bug = (function () { Bug.prototype.foo = function (name) { this.name = name; }; + Bug.func = [ + function (that, name) { + that.foo(name); + } + ]; return Bug; }()); -Bug.func = [ - function (that, name) { - that.foo(name); - } -]; // Valid use of this in a property bound decl var A = (function () { function A() { diff --git a/tests/baselines/reference/thisInStaticMethod1.js b/tests/baselines/reference/thisInStaticMethod1.js index 1e39ded3b61..a42415c0b62 100644 --- a/tests/baselines/reference/thisInStaticMethod1.js +++ b/tests/baselines/reference/thisInStaticMethod1.js @@ -14,7 +14,7 @@ var foo = (function () { foo.bar = function () { return this.x; }; + foo.x = 3; return foo; }()); -foo.x = 3; var x = foo.bar(); diff --git a/tests/baselines/reference/thisTypeErrors.js b/tests/baselines/reference/thisTypeErrors.js index 5811ec6b709..f246b80f4f4 100644 --- a/tests/baselines/reference/thisTypeErrors.js +++ b/tests/baselines/reference/thisTypeErrors.js @@ -75,9 +75,9 @@ var C2 = (function () { C2.foo = function (x) { return undefined; }; + C2.y = undefined; return C2; }()); -C2.y = undefined; var N1; (function (N1) { N1.y = this; diff --git a/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with CommonJS option.js b/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with CommonJS option.js index cd4ce3c862e..9bdbfba8396 100644 --- a/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with CommonJS option.js +++ b/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with CommonJS option.js @@ -14,11 +14,11 @@ var MyClass1 = (function () { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + fooexport, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); -MyClass1 = __decorate([ - fooexport, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) -], MyClass1); -var _a; //# sourceMappingURL=file.js.map \ No newline at end of file diff --git a/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with System option.js b/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with System option.js index 9e3d59ce27c..e79eeceae50 100644 --- a/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with System option.js +++ b/tests/baselines/reference/transpile/Correctly serialize metadata when transpile with System option.js @@ -10,7 +10,7 @@ System.register(["angular2/core"], function (exports_1, context_1) { if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v); }; var __moduleName = context_1 && context_1.id; - var ng, MyClass1, _a; + var ng, MyClass1; return { setters: [ function (ng_1) { @@ -22,12 +22,13 @@ System.register(["angular2/core"], function (exports_1, context_1) { function MyClass1(_elementRef) { this._elementRef = _elementRef; } + MyClass1 = __decorate([ + fooexport, + __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) + ], MyClass1); return MyClass1; + var _a; }()); - MyClass1 = __decorate([ - fooexport, - __metadata("design:paramtypes", [typeof (_a = (typeof ng !== "undefined" && ng).ElementRef) === "function" && _a || Object]) - ], MyClass1); } }; }); diff --git a/tests/baselines/reference/transpile/Transpile with emit decorators and emit metadata.js b/tests/baselines/reference/transpile/Transpile with emit decorators and emit metadata.js index 0b3bbaa8d73..236f91f9594 100644 --- a/tests/baselines/reference/transpile/Transpile with emit decorators and emit metadata.js +++ b/tests/baselines/reference/transpile/Transpile with emit decorators and emit metadata.js @@ -9,12 +9,12 @@ var MyClass = (function () { this.db = db; this.db.doSomething(); } + MyClass = __decorate([ + someDecorator, + __metadata("design:paramtypes", [typeof (_a = typeof db_1.db !== "undefined" && db_1.db) === "function" && _a || Object]) + ], MyClass); return MyClass; + var _a; }()); -MyClass = __decorate([ - someDecorator, - __metadata("design:paramtypes", [typeof (_a = typeof db_1.db !== "undefined" && db_1.db) === "function" && _a || Object]) -], MyClass); exports.MyClass = MyClass; -var _a; //# sourceMappingURL=file.js.map \ No newline at end of file diff --git a/tests/baselines/reference/tsxDefaultImports.js b/tests/baselines/reference/tsxDefaultImports.js index a6c1a4217a3..c3a287c478d 100644 --- a/tests/baselines/reference/tsxDefaultImports.js +++ b/tests/baselines/reference/tsxDefaultImports.js @@ -23,9 +23,9 @@ var SomeEnum; var SomeClass = (function () { function SomeClass() { } + SomeClass.E = SomeEnum; return SomeClass; }()); -SomeClass.E = SomeEnum; exports["default"] = SomeClass; //// [b.js] "use strict"; diff --git a/tests/baselines/reference/typeOfPrototype.js b/tests/baselines/reference/typeOfPrototype.js index a0f076113e0..3e8b3186936 100644 --- a/tests/baselines/reference/typeOfPrototype.js +++ b/tests/baselines/reference/typeOfPrototype.js @@ -11,7 +11,7 @@ var Foo = (function () { function Foo() { this.bar = 3; } + Foo.bar = ''; return Foo; }()); -Foo.bar = ''; Foo.prototype.bar = undefined; // Should be OK diff --git a/tests/baselines/reference/typeOfThisInStaticMembers2.js b/tests/baselines/reference/typeOfThisInStaticMembers2.js index 886ea04e23d..b01770446be 100644 --- a/tests/baselines/reference/typeOfThisInStaticMembers2.js +++ b/tests/baselines/reference/typeOfThisInStaticMembers2.js @@ -11,12 +11,12 @@ class C2 { var C = (function () { function C() { } + C.foo = this; // error return C; }()); -C.foo = this; // error var C2 = (function () { function C2() { } + C2.foo = this; // error return C2; }()); -C2.foo = this; // error diff --git a/tests/baselines/reference/typeQueryOnClass.js b/tests/baselines/reference/typeQueryOnClass.js index 80623af5be8..85dff0de831 100644 --- a/tests/baselines/reference/typeQueryOnClass.js +++ b/tests/baselines/reference/typeQueryOnClass.js @@ -99,10 +99,10 @@ var C = (function () { enumerable: true, configurable: true }); + C.sa = 1; + C.sb = function () { return 1; }; return C; }()); -C.sa = 1; -C.sb = function () { return 1; }; var c; // BUG 820454 var r1; diff --git a/tests/baselines/reference/typeofUsedBeforeBlockScoped.js b/tests/baselines/reference/typeofUsedBeforeBlockScoped.js index eebf4beae67..cc9003dd4f6 100644 --- a/tests/baselines/reference/typeofUsedBeforeBlockScoped.js +++ b/tests/baselines/reference/typeofUsedBeforeBlockScoped.js @@ -12,8 +12,8 @@ let o = { n: 12 }; var C = (function () { function C() { } + C.s = 2; return C; }()); -C.s = 2; var o2; var o = { n: 12 }; diff --git a/tests/baselines/reference/unqualifiedCallToClassStatic1.js b/tests/baselines/reference/unqualifiedCallToClassStatic1.js index 906e9d3795f..6c78a737fe8 100644 --- a/tests/baselines/reference/unqualifiedCallToClassStatic1.js +++ b/tests/baselines/reference/unqualifiedCallToClassStatic1.js @@ -10,9 +10,9 @@ class Vector { var Vector = (function () { function Vector() { } + Vector.foo = function () { + // 'foo' cannot be called in an unqualified manner. + foo(); + }; return Vector; }()); -Vector.foo = function () { - // 'foo' cannot be called in an unqualified manner. - foo(); -}; diff --git a/tests/baselines/reference/witness.js b/tests/baselines/reference/witness.js index 9f92c90ffa4..ebd1669d177 100644 --- a/tests/baselines/reference/witness.js +++ b/tests/baselines/reference/witness.js @@ -258,9 +258,9 @@ var c2inst; var C3 = (function () { function C3() { } + C3.q = C3.q; return C3; }()); -C3.q = C3.q; var qq = C3.q; var qq; // Parentheses - tested a bunch above From fe838bab2d5180d35110725a0a035ce4e8cdbe04 Mon Sep 17 00:00:00 2001 From: Yui T Date: Sat, 27 May 2017 19:10:53 -0700 Subject: [PATCH 33/56] Parse ts-style property tag --- src/compiler/parser.ts | 31 +++++++------------------------ src/compiler/types.ts | 4 ++++ 2 files changed, 11 insertions(+), 24 deletions(-) diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index cd9cd7c247d..575992ca1a1 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6508,7 +6508,7 @@ namespace ts { case "arg": case "argument": case "param": - tag = parseParamTag(atToken, tagName); + tag = parseParameterOrPropertyTag(atToken, tagName, /*shouldParseParamTag*/ true); break; case "return": case "returns": @@ -6653,11 +6653,12 @@ namespace ts { return { name, isBracketed }; } - function parseParamTag(atToken: AtToken, tagName: Identifier) { + function parseParameterOrPropertyTag(atToken: AtToken, tagName: Identifier, shouldParseParamTag: boolean): JSDocPropertyTag | JSDocParameterTag { let typeExpression = tryParseTypeExpression(); skipWhitespace(); const { name, isBracketed } = parseBracketNameInPropertyAndParamTag(); + skipWhitespace(); if (!name) { parseErrorAtPosition(scanner.getStartPos(), 0, Diagnostics.Identifier_expected); @@ -6676,7 +6677,9 @@ namespace ts { typeExpression = tryParseTypeExpression(); } - const result = createNode(SyntaxKind.JSDocParameterTag, atToken.pos); + const result = shouldParseParamTag ? + createNode(SyntaxKind.JSDocParameterTag, atToken.pos) : + createNode(SyntaxKind.JSDocPropertyTag, atToken.pos); result.atToken = atToken; result.tagName = tagName; result.preParameterName = preName; @@ -6711,26 +6714,6 @@ namespace ts { return finishNode(result); } - function parsePropertyTag(atToken: AtToken, tagName: Identifier): JSDocPropertyTag { - const typeExpression = tryParseTypeExpression(); - skipWhitespace(); - const { name, isBracketed } = parseBracketNameInPropertyAndParamTag(); - skipWhitespace(); - - if (!name) { - parseErrorAtPosition(scanner.getStartPos(), /*length*/ 0, Diagnostics.Identifier_expected); - return undefined; - } - - const result = createNode(SyntaxKind.JSDocPropertyTag, atToken.pos); - result.atToken = atToken; - result.tagName = tagName; - result.name = name; - result.typeExpression = typeExpression; - result.isBracketed = isBracketed; - return finishNode(result); - } - function parseAugmentsTag(atToken: AtToken, tagName: Identifier): JSDocAugmentsTag { const typeExpression = tryParseTypeExpression(); @@ -6867,7 +6850,7 @@ namespace ts { return true; case "prop": case "property": - const propertyTag = parsePropertyTag(atToken, tagName); + const propertyTag = parseParameterOrPropertyTag(atToken, tagName, /*shouldParseParamTag*/ false) as JSDocPropertyTag; if (propertyTag) { if (!parentTag.jsDocPropertyTags) { parentTag.jsDocPropertyTags = >[]; diff --git a/src/compiler/types.ts b/src/compiler/types.ts index d8d6c174c12..ebb0f02f39d 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -2145,6 +2145,10 @@ namespace ts { parent: JSDoc; kind: SyntaxKind.JSDocPropertyTag; name: Identifier; + /** the parameter name, if provided *before* the type (TypeScript-style) */ + preParameterName?: Identifier; + /** the parameter name, if provided *after* the type (JSDoc-standard) */ + postParameterName?: Identifier; typeExpression: JSDocTypeExpression; isBracketed: boolean; } From 227198fae175734acf2ea66ddee930315806bdb8 Mon Sep 17 00:00:00 2001 From: Yui T Date: Sat, 27 May 2017 19:11:08 -0700 Subject: [PATCH 34/56] Add tests and update baselines --- ...parsesCorrectly.argSynonymForParamTag.json | 4 +-- ...sCorrectly.argumentSynonymForParamTag.json | 4 +-- ...cComments.parsesCorrectly.oneParamTag.json | 4 +-- ...DocComments.parsesCorrectly.paramTag1.json | 4 +-- ...ents.parsesCorrectly.paramWithoutType.json | 4 +-- ...Comments.parsesCorrectly.twoParamTag2.json | 6 ++-- ...parsesCorrectly.twoParamTagOnSameLine.json | 6 ++-- ...sCorrectly.typedefTagWithChildrenTags.json | 36 ++++++++++++------- .../reference/checkJsdocTypedefInParamTag1.js | 22 +++++++++++- .../checkJsdocTypedefInParamTag1.symbols | 15 ++++++++ .../checkJsdocTypedefInParamTag1.types | 18 ++++++++++ .../jsdoc/checkJsdocTypedefInParamTag1.ts | 13 ++++++- 12 files changed, 106 insertions(+), 30 deletions(-) diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json index 7e4346eba68..92b9cb450e6 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argSynonymForParamTag.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 27, + "end": 28, "atToken": { "kind": "AtToken", "pos": 8, @@ -44,6 +44,6 @@ }, "length": 1, "pos": 8, - "end": 27 + "end": 28 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json index e46a09e6561..f398fb3af41 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.argumentSynonymForParamTag.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 32, + "end": 33, "atToken": { "kind": "AtToken", "pos": 8, @@ -44,6 +44,6 @@ }, "length": 1, "pos": 8, - "end": 32 + "end": 33 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json index af20bf8d6bb..e70fc95367f 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.oneParamTag.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 29, + "end": 30, "atToken": { "kind": "AtToken", "pos": 8, @@ -44,6 +44,6 @@ }, "length": 1, "pos": 8, - "end": 29 + "end": 30 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json index 5e0c3d21744..0dbdd83d2ba 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramTag1.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 29, + "end": 30, "atToken": { "kind": "AtToken", "pos": 8, @@ -44,6 +44,6 @@ }, "length": 1, "pos": 8, - "end": 29 + "end": 30 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json index 17036e3729a..2ff182483d9 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.paramWithoutType.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 18, + "end": 19, "atToken": { "kind": "AtToken", "pos": 8, @@ -34,6 +34,6 @@ }, "length": 1, "pos": 8, - "end": 18 + "end": 19 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json index d5d04dce69c..b51ab3598e6 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTag2.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 29, + "end": 32, "atToken": { "kind": "AtToken", "pos": 8, @@ -45,7 +45,7 @@ "1": { "kind": "JSDocParameterTag", "pos": 34, - "end": 55, + "end": 56, "atToken": { "kind": "AtToken", "pos": 34, @@ -83,6 +83,6 @@ }, "length": 2, "pos": 8, - "end": 55 + "end": 56 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json index 4c85b2c9aed..3c20d5edcbc 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.twoParamTagOnSameLine.json @@ -6,7 +6,7 @@ "0": { "kind": "JSDocParameterTag", "pos": 8, - "end": 29, + "end": 30, "atToken": { "kind": "AtToken", "pos": 8, @@ -45,7 +45,7 @@ "1": { "kind": "JSDocParameterTag", "pos": 30, - "end": 51, + "end": 52, "atToken": { "kind": "AtToken", "pos": 30, @@ -83,6 +83,6 @@ }, "length": 2, "pos": 8, - "end": 51 + "end": 52 } } \ No newline at end of file diff --git a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.typedefTagWithChildrenTags.json b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.typedefTagWithChildrenTags.json index 7ef64f5a971..7a8f9c4bcc9 100644 --- a/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.typedefTagWithChildrenTags.json +++ b/tests/baselines/reference/JSDocParsing/DocComments.parsesCorrectly.typedefTagWithChildrenTags.json @@ -82,12 +82,6 @@ "end": 56, "text": "property" }, - "name": { - "kind": "Identifier", - "pos": 66, - "end": 69, - "text": "age" - }, "typeExpression": { "kind": "JSDocTypeExpression", "pos": 57, @@ -97,6 +91,18 @@ "pos": 58, "end": 64 } + }, + "postParameterName": { + "kind": "Identifier", + "pos": 66, + "end": 69, + "text": "age" + }, + "name": { + "kind": "Identifier", + "pos": 66, + "end": 69, + "text": "age" } }, { @@ -114,12 +120,6 @@ "end": 83, "text": "property" }, - "name": { - "kind": "Identifier", - "pos": 93, - "end": 97, - "text": "name" - }, "typeExpression": { "kind": "JSDocTypeExpression", "pos": 84, @@ -129,6 +129,18 @@ "pos": 85, "end": 91 } + }, + "postParameterName": { + "kind": "Identifier", + "pos": 93, + "end": 97, + "text": "name" + }, + "name": { + "kind": "Identifier", + "pos": 93, + "end": 97, + "text": "name" } } ] diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js index d4983bfd581..8ef81a71cb8 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js @@ -11,7 +11,18 @@ */ function foo(opts) {} -foo({x: 'abc'}); +foo({x: 'abc'}); + +/** + * @typedef {Object} AnotherOpts + * @property anotherX {string} + * @property anotherY {string=} + * + * @param {AnotherOpts} opts + */ +function foo1(opts) {} + +foo1({anotherX: "world"}); //// [0.js] // @ts-check @@ -26,3 +37,12 @@ foo({x: 'abc'}); */ function foo(opts) { } foo({ x: 'abc' }); +/** + * @typedef {Object} AnotherOpts + * @property anotherX {string} + * @property anotherY {string=} + * + * @param {AnotherOpts} opts + */ +function foo1(opts) { } +foo1({ anotherX: "world" }); diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols index cd2455797b4..596e5ca89c5 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols @@ -17,3 +17,18 @@ foo({x: 'abc'}); >foo : Symbol(foo, Decl(0.js, 0, 0)) >x : Symbol(x, Decl(0.js, 12, 5)) +/** + * @typedef {Object} AnotherOpts + * @property anotherX {string} + * @property anotherY {string=} + * + * @param {AnotherOpts} opts + */ +function foo1(opts) {} +>foo1 : Symbol(foo1, Decl(0.js, 12, 16)) +>opts : Symbol(opts, Decl(0.js, 21, 14)) + +foo1({anotherX: "world"}); +>foo1 : Symbol(foo1, Decl(0.js, 12, 16)) +>anotherX : Symbol(anotherX, Decl(0.js, 23, 6)) + diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types index cc923e33030..82b17d71a4a 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types @@ -20,3 +20,21 @@ foo({x: 'abc'}); >x : string >'abc' : "abc" +/** + * @typedef {Object} AnotherOpts + * @property anotherX {string} + * @property anotherY {string=} + * + * @param {AnotherOpts} opts + */ +function foo1(opts) {} +>foo1 : (opts: { anotherX: string; anotherY?: string; }) => void +>opts : { anotherX: string; anotherY?: string; } + +foo1({anotherX: "world"}); +>foo1({anotherX: "world"}) : void +>foo1 : (opts: { anotherX: string; anotherY?: string; }) => void +>{anotherX: "world"} : { anotherX: string; } +>anotherX : string +>"world" : "world" + diff --git a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts index 80ca21bd4ff..853a65766ce 100644 --- a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts +++ b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts @@ -14,4 +14,15 @@ */ function foo(opts) {} -foo({x: 'abc'}); \ No newline at end of file +foo({x: 'abc'}); + +/** + * @typedef {Object} AnotherOpts + * @property anotherX {string} + * @property anotherY {string=} + * + * @param {AnotherOpts} opts + */ +function foo1(opts) {} + +foo1({anotherX: "world"}); \ No newline at end of file From 4838eff2d7b0833c62b6e9e667fd3d5e006cf070 Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 20:37:01 -0700 Subject: [PATCH 35/56] "function" without followed by "(" should be considered as Global function type --- src/compiler/checker.ts | 1 + src/compiler/parser.ts | 5 ++++- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 125e492cc39..9ff1c4b41b9 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -6855,6 +6855,7 @@ namespace ts { case "Object": return anyType; case "Function": + case "function": return globalFunctionType; case "Array": case "array": diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 07d4a9ada41..04d70639e12 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6075,7 +6075,10 @@ namespace ts { case SyntaxKind.OpenBraceToken: return parseJSDocRecordType(); case SyntaxKind.FunctionKeyword: - return parseJSDocFunctionType(); + if (lookAhead(nextTokenIsOpenParen)) { + return parseJSDocFunctionType(); + } + break; case SyntaxKind.DotDotDotToken: return parseJSDocVariadicType(); case SyntaxKind.NewKeyword: From 0ead501c86203d3c5473acaaf98e1c61ad0c5bab Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 20:37:15 -0700 Subject: [PATCH 36/56] Update tests and baselines --- tests/baselines/reference/jsDocTypeTag2.js | 24 ++---------------- tests/baselines/reference/jsDocTypes2.js | 7 ++++++ tests/baselines/reference/jsDocTypes2.symbols | 25 +++++++++++++------ tests/baselines/reference/jsDocTypes2.types | 14 +++++++++++ tests/cases/conformance/salsa/jsDocTypes2.ts | 4 +++ 5 files changed, 44 insertions(+), 30 deletions(-) diff --git a/tests/baselines/reference/jsDocTypeTag2.js b/tests/baselines/reference/jsDocTypeTag2.js index 07535dcee08..d54b4557f06 100644 --- a/tests/baselines/reference/jsDocTypeTag2.js +++ b/tests/baselines/reference/jsDocTypeTag2.js @@ -431,28 +431,8 @@ "kind": "space" }, { - "text": "(", - "kind": "punctuation" - }, - { - "text": ")", - "kind": "punctuation" - }, - { - "text": " ", - "kind": "space" - }, - { - "text": "=>", - "kind": "punctuation" - }, - { - "text": " ", - "kind": "space" - }, - { - "text": "any", - "kind": "keyword" + "text": "Function", + "kind": "localName" } ], "documentation": [], diff --git a/tests/baselines/reference/jsDocTypes2.js b/tests/baselines/reference/jsDocTypes2.js index a3848704fad..ba59043978c 100644 --- a/tests/baselines/reference/jsDocTypes2.js +++ b/tests/baselines/reference/jsDocTypes2.js @@ -11,6 +11,10 @@ anyT1 = "hi"; const x = (a) => a + 1; x(1); +/** @type {function} */ +const y = (a) => a + 1; +x(1); + /** @type {function (number)} */ const x1 = (a) => a + 1; x1(0); @@ -29,6 +33,9 @@ anyT1 = "hi"; /** @type {Function} */ var x = function (a) { return a + 1; }; x(1); +/** @type {function} */ +var y = function (a) { return a + 1; }; +x(1); /** @type {function (number)} */ var x1 = function (a) { return a + 1; }; x1(0); diff --git a/tests/baselines/reference/jsDocTypes2.symbols b/tests/baselines/reference/jsDocTypes2.symbols index 96b32b9ad91..8f4dc4e7b43 100644 --- a/tests/baselines/reference/jsDocTypes2.symbols +++ b/tests/baselines/reference/jsDocTypes2.symbols @@ -20,21 +20,30 @@ const x = (a) => a + 1; x(1); >x : Symbol(x, Decl(0.js, 9, 5)) +/** @type {function} */ +const y = (a) => a + 1; +>y : Symbol(y, Decl(0.js, 13, 5)) +>a : Symbol(a, Decl(0.js, 13, 11)) +>a : Symbol(a, Decl(0.js, 13, 11)) + +x(1); +>x : Symbol(x, Decl(0.js, 9, 5)) + /** @type {function (number)} */ const x1 = (a) => a + 1; ->x1 : Symbol(x1, Decl(0.js, 13, 5)) ->a : Symbol(a, Decl(0.js, 13, 12)) ->a : Symbol(a, Decl(0.js, 13, 12)) +>x1 : Symbol(x1, Decl(0.js, 17, 5)) +>a : Symbol(a, Decl(0.js, 17, 12)) +>a : Symbol(a, Decl(0.js, 17, 12)) x1(0); ->x1 : Symbol(x1, Decl(0.js, 13, 5)) +>x1 : Symbol(x1, Decl(0.js, 17, 5)) /** @type {function (number): number} */ const x2 = (a) => a + 1; ->x2 : Symbol(x2, Decl(0.js, 17, 5)) ->a : Symbol(a, Decl(0.js, 17, 12)) ->a : Symbol(a, Decl(0.js, 17, 12)) +>x2 : Symbol(x2, Decl(0.js, 21, 5)) +>a : Symbol(a, Decl(0.js, 21, 12)) +>a : Symbol(a, Decl(0.js, 21, 12)) x2(0); ->x2 : Symbol(x2, Decl(0.js, 17, 5)) +>x2 : Symbol(x2, Decl(0.js, 21, 5)) diff --git a/tests/baselines/reference/jsDocTypes2.types b/tests/baselines/reference/jsDocTypes2.types index db5a5902d10..599c19c7ffc 100644 --- a/tests/baselines/reference/jsDocTypes2.types +++ b/tests/baselines/reference/jsDocTypes2.types @@ -29,6 +29,20 @@ x(1); >x : Function >1 : 1 +/** @type {function} */ +const y = (a) => a + 1; +>y : Function +>(a) => a + 1 : (a: any) => any +>a : any +>a + 1 : any +>a : any +>1 : 1 + +x(1); +>x(1) : any +>x : Function +>1 : 1 + /** @type {function (number)} */ const x1 = (a) => a + 1; >x1 : (arg0: number) => any diff --git a/tests/cases/conformance/salsa/jsDocTypes2.ts b/tests/cases/conformance/salsa/jsDocTypes2.ts index 612804b91d7..21107f87ccf 100644 --- a/tests/cases/conformance/salsa/jsDocTypes2.ts +++ b/tests/cases/conformance/salsa/jsDocTypes2.ts @@ -14,6 +14,10 @@ anyT1 = "hi"; const x = (a) => a + 1; x(1); +/** @type {function} */ +const y = (a) => a + 1; +x(1); + /** @type {function (number)} */ const x1 = (a) => a + 1; x1(0); From 10eae61aca469a590b80260e894b1816721cf9f4 Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 21:47:39 -0700 Subject: [PATCH 37/56] Handle "object" as "Object" in JSDoc type expression --- src/compiler/parser.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 07d4a9ada41..2d44f2eed7c 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6091,7 +6091,6 @@ namespace ts { case SyntaxKind.NullKeyword: case SyntaxKind.UndefinedKeyword: case SyntaxKind.NeverKeyword: - case SyntaxKind.ObjectKeyword: return parseTokenNode(); case SyntaxKind.StringLiteral: case SyntaxKind.NumericLiteral: @@ -6769,7 +6768,7 @@ namespace ts { const jsDocTypeReference = typeExpression.type; if (jsDocTypeReference.name.kind === SyntaxKind.Identifier) { const name = jsDocTypeReference.name; - if (name.text === "Object") { + if (name.text === "Object" || name.text === "object") { typedefTag.jsDocTypeLiteral = scanChildTags(); } } From 5c7c113203a82c10f99834403eb166ab81a2ae4c Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 21:48:34 -0700 Subject: [PATCH 38/56] Update tests and baselines --- .../reference/checkJsdocTypedefInParamTag1.js | 38 +++++++++++++++++-- .../checkJsdocTypedefInParamTag1.symbols | 32 +++++++++++++++- .../checkJsdocTypedefInParamTag1.types | 33 +++++++++++++++- .../jsdoc/checkJsdocTypedefInParamTag1.ts | 22 +++++++++-- 4 files changed, 116 insertions(+), 9 deletions(-) diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js index d4983bfd581..7ce5cdd6f38 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js @@ -9,9 +9,26 @@ * * @param {Opts} opts */ -function foo(opts) {} +function foo(opts) { + opts.x; +} -foo({x: 'abc'}); +foo({x: 'abc'}); + +/** + * @typedef {object} Opts1 + * @property {string} x + * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] + * + * @param {Opts1} opts + */ +function foo1(opts) { + opts.x; +} +foo1({x: 'abc'}); + //// [0.js] // @ts-check @@ -24,5 +41,20 @@ foo({x: 'abc'}); * * @param {Opts} opts */ -function foo(opts) { } +function foo(opts) { + opts.x; +} foo({ x: 'abc' }); +/** + * @typedef {object} Opts1 + * @property {string} x + * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] + * + * @param {Opts1} opts + */ +function foo1(opts) { + opts.x; +} +foo1({ x: 'abc' }); diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols index cd2455797b4..be4c40643d0 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols @@ -9,11 +9,39 @@ * * @param {Opts} opts */ -function foo(opts) {} +function foo(opts) { >foo : Symbol(foo, Decl(0.js, 0, 0)) >opts : Symbol(opts, Decl(0.js, 10, 13)) + opts.x; +>opts.x : Symbol(x, Decl(0.js, 3, 3)) +>opts : Symbol(opts, Decl(0.js, 10, 13)) +>x : Symbol(x, Decl(0.js, 3, 3)) +} + foo({x: 'abc'}); >foo : Symbol(foo, Decl(0.js, 0, 0)) ->x : Symbol(x, Decl(0.js, 12, 5)) +>x : Symbol(x, Decl(0.js, 14, 5)) + +/** + * @typedef {object} Opts1 + * @property {string} x + * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] + * + * @param {Opts1} opts + */ +function foo1(opts) { +>foo1 : Symbol(foo1, Decl(0.js, 14, 16)) +>opts : Symbol(opts, Decl(0.js, 25, 14)) + + opts.x; +>opts.x : Symbol(x, Decl(0.js, 18, 3)) +>opts : Symbol(opts, Decl(0.js, 25, 14)) +>x : Symbol(x, Decl(0.js, 18, 3)) +} +foo1({x: 'abc'}); +>foo1 : Symbol(foo1, Decl(0.js, 14, 16)) +>x : Symbol(x, Decl(0.js, 28, 6)) diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types index cc923e33030..a82b125a2ba 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types @@ -9,10 +9,16 @@ * * @param {Opts} opts */ -function foo(opts) {} +function foo(opts) { >foo : (opts: { x: string; y?: string; z?: string; w?: string; }) => void >opts : { x: string; y?: string; z?: string; w?: string; } + opts.x; +>opts.x : string +>opts : { x: string; y?: string; z?: string; w?: string; } +>x : string +} + foo({x: 'abc'}); >foo({x: 'abc'}) : void >foo : (opts: { x: string; y?: string; z?: string; w?: string; }) => void @@ -20,3 +26,28 @@ foo({x: 'abc'}); >x : string >'abc' : "abc" +/** + * @typedef {object} Opts1 + * @property {string} x + * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] + * + * @param {Opts1} opts + */ +function foo1(opts) { +>foo1 : (opts: { x: string; y?: string; z?: string; w?: string; }) => void +>opts : { x: string; y?: string; z?: string; w?: string; } + + opts.x; +>opts.x : string +>opts : { x: string; y?: string; z?: string; w?: string; } +>x : string +} +foo1({x: 'abc'}); +>foo1({x: 'abc'}) : void +>foo1 : (opts: { x: string; y?: string; z?: string; w?: string; }) => void +>{x: 'abc'} : { x: string; } +>x : string +>'abc' : "abc" + diff --git a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts index 80ca21bd4ff..fa885b9f316 100644 --- a/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts +++ b/tests/cases/conformance/jsdoc/checkJsdocTypedefInParamTag1.ts @@ -9,9 +9,25 @@ * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts} opts */ -function foo(opts) {} +function foo(opts) { + opts.x; +} -foo({x: 'abc'}); \ No newline at end of file +foo({x: 'abc'}); + +/** + * @typedef {object} Opts1 + * @property {string} x + * @property {string=} y + * @property {string} [z] + * @property {string} [w="hi"] + * + * @param {Opts1} opts + */ +function foo1(opts) { + opts.x; +} +foo1({x: 'abc'}); From d35e538123ecfd6cde1fe3b4872d8fe6a47c73dd Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 21:48:43 -0700 Subject: [PATCH 39/56] Add fourslash tests --- tests/baselines/reference/jsDocTypedef1.js | 234 ++++++++++++++++++ .../cases/fourslash/jsDocTypedefQuickInfo1.ts | 33 +++ 2 files changed, 267 insertions(+) create mode 100644 tests/baselines/reference/jsDocTypedef1.js create mode 100644 tests/cases/fourslash/jsDocTypedefQuickInfo1.ts diff --git a/tests/baselines/reference/jsDocTypedef1.js b/tests/baselines/reference/jsDocTypedef1.js new file mode 100644 index 00000000000..28410ee8795 --- /dev/null +++ b/tests/baselines/reference/jsDocTypedef1.js @@ -0,0 +1,234 @@ +[ + { + "marker": { + "fileName": "/tests/cases/fourslash/jsDocTypedef1.js", + "position": 189 + }, + "quickInfo": { + "kind": "parameter", + "kindModifiers": "", + "textSpan": { + "start": 189, + "length": 4 + }, + "displayParts": [ + { + "text": "(", + "kind": "punctuation" + }, + { + "text": "parameter", + "kind": "text" + }, + { + "text": ")", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "opts", + "kind": "parameterName" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "{", + "kind": "punctuation" + }, + { + "text": "\n", + "kind": "lineBreak" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "x", + "kind": "propertyName" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "string", + "kind": "keyword" + }, + { + "text": ";", + "kind": "punctuation" + }, + { + "text": "\n", + "kind": "lineBreak" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "y", + "kind": "propertyName" + }, + { + "text": "?", + "kind": "punctuation" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "string", + "kind": "keyword" + }, + { + "text": ";", + "kind": "punctuation" + }, + { + "text": "\n", + "kind": "lineBreak" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "z", + "kind": "propertyName" + }, + { + "text": "?", + "kind": "punctuation" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "string", + "kind": "keyword" + }, + { + "text": ";", + "kind": "punctuation" + }, + { + "text": "\n", + "kind": "lineBreak" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "w", + "kind": "propertyName" + }, + { + "text": "?", + "kind": "punctuation" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "string", + "kind": "keyword" + }, + { + "text": ";", + "kind": "punctuation" + }, + { + "text": "\n", + "kind": "lineBreak" + }, + { + "text": "}", + "kind": "punctuation" + } + ], + "documentation": [], + "tags": [] + } + }, + { + "marker": { + "fileName": "/tests/cases/fourslash/jsDocTypedef1.js", + "position": 424 + }, + "quickInfo": { + "kind": "parameter", + "kindModifiers": "", + "textSpan": { + "start": 424, + "length": 5 + }, + "displayParts": [ + { + "text": "(", + "kind": "punctuation" + }, + { + "text": "parameter", + "kind": "text" + }, + { + "text": ")", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "opts1", + "kind": "parameterName" + }, + { + "text": ":", + "kind": "punctuation" + }, + { + "text": " ", + "kind": "space" + }, + { + "text": "any", + "kind": "keyword" + } + ], + "documentation": [], + "tags": [] + } + } +] \ No newline at end of file diff --git a/tests/cases/fourslash/jsDocTypedefQuickInfo1.ts b/tests/cases/fourslash/jsDocTypedefQuickInfo1.ts new file mode 100644 index 00000000000..eea17f182e9 --- /dev/null +++ b/tests/cases/fourslash/jsDocTypedefQuickInfo1.ts @@ -0,0 +1,33 @@ +/// +// @allowJs: true +// @Filename: jsDocTypedef1.js +//// /** +//// * @typedef {Object} Opts +//// * @property {string} x +//// * @property {string=} y +//// * @property {string} [z] +//// * @property {string} [w="hi"] +//// * +//// * @param {Opts} opts +//// */ +//// function foo(/*1*/opts) { +//// opts.x; +///// } + +//// foo({x: 'abc'}); + +//// /** +//// * @typedef {object} Opts1 +//// * @property {string} x +//// * @property {string=} y +//// * @property {string} [z] +//// * @property {string} [w="hi"] +//// * +//// * @param {Opts1} opts +//// */ +//// function foo1(/*2*/opts1) { +//// opts1.x; +//// } +//// foo1({x: 'abc'}); + +verify.baselineQuickInfo(); \ No newline at end of file From 1e8edcbad44223d2b11f72e3eace211c12f32ff2 Mon Sep 17 00:00:00 2001 From: Yui T Date: Mon, 29 May 2017 21:55:55 -0700 Subject: [PATCH 40/56] remove whitespace --- tests/baselines/reference/checkJsdocTypedefInParamTag1.js | 4 ++-- .../baselines/reference/checkJsdocTypedefInParamTag1.symbols | 4 ++-- tests/baselines/reference/checkJsdocTypedefInParamTag1.types | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js index 7ce5cdd6f38..cc2e302ffca 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.js +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.js @@ -6,7 +6,7 @@ * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts} opts */ function foo(opts) { @@ -21,7 +21,7 @@ foo({x: 'abc'}); * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts1} opts */ function foo1(opts) { diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols index be4c40643d0..844c4c045aa 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.symbols @@ -6,7 +6,7 @@ * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts} opts */ function foo(opts) { @@ -29,7 +29,7 @@ foo({x: 'abc'}); * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts1} opts */ function foo1(opts) { diff --git a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types index a82b125a2ba..cb21ea2ef06 100644 --- a/tests/baselines/reference/checkJsdocTypedefInParamTag1.types +++ b/tests/baselines/reference/checkJsdocTypedefInParamTag1.types @@ -6,7 +6,7 @@ * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts} opts */ function foo(opts) { @@ -32,7 +32,7 @@ foo({x: 'abc'}); * @property {string=} y * @property {string} [z] * @property {string} [w="hi"] - * + * * @param {Opts1} opts */ function foo1(opts) { From e3e81b867303ce50399ae593ee6a27afbb0f1b1a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Kate=20Mih=C3=A1likov=C3=A1?= Date: Mon, 29 May 2017 13:40:41 +0200 Subject: [PATCH 41/56] Add support for diff3-style conflict --- src/compiler/scanner.ts | 22 +++++++++++++++++----- src/services/classifier.ts | 10 +++++----- 2 files changed, 22 insertions(+), 10 deletions(-) diff --git a/src/compiler/scanner.ts b/src/compiler/scanner.ts index d27bbf879fe..0a072a3b8ac 100644 --- a/src/compiler/scanner.ts +++ b/src/compiler/scanner.ts @@ -429,6 +429,7 @@ namespace ts { case CharacterCodes.slash: // starts of normal trivia case CharacterCodes.lessThan: + case CharacterCodes.bar: case CharacterCodes.equals: case CharacterCodes.greaterThan: // Starts of conflict marker trivia @@ -496,6 +497,7 @@ namespace ts { break; case CharacterCodes.lessThan: + case CharacterCodes.bar: case CharacterCodes.equals: case CharacterCodes.greaterThan: if (isConflictMarkerTrivia(text, pos)) { @@ -562,12 +564,12 @@ namespace ts { } } else { - Debug.assert(ch === CharacterCodes.equals); - // Consume everything from the start of the mid-conflict marker to the start of the next - // end-conflict marker. + Debug.assert(ch === CharacterCodes.bar || ch === CharacterCodes.equals); + // Consume everything from the start of a ||||||| or ======= marker to the start + // of the next ======= or >>>>>>> marker. while (pos < len) { - const ch = text.charCodeAt(pos); - if (ch === CharacterCodes.greaterThan && isConflictMarkerTrivia(text, pos)) { + const currentChar = text.charCodeAt(pos); + if ((currentChar === CharacterCodes.equals || currentChar === CharacterCodes.greaterThan) && currentChar !== ch && isConflictMarkerTrivia(text, pos)) { break; } @@ -1562,6 +1564,16 @@ namespace ts { pos++; return token = SyntaxKind.OpenBraceToken; case CharacterCodes.bar: + if (isConflictMarkerTrivia(text, pos)) { + pos = scanConflictMarkerTrivia(text, pos, error); + if (skipTrivia) { + continue; + } + else { + return token = SyntaxKind.ConflictMarkerTrivia; + } + } + if (text.charCodeAt(pos + 1) === CharacterCodes.bar) { return pos += 2, token = SyntaxKind.BarBarToken; } diff --git a/src/services/classifier.ts b/src/services/classifier.ts index acee8fe4b0e..beeddda434e 100644 --- a/src/services/classifier.ts +++ b/src/services/classifier.ts @@ -685,9 +685,9 @@ namespace ts { continue; } - // for the ======== add a comment for the first line, and then lex all - // subsequent lines up until the end of the conflict marker. - Debug.assert(ch === CharacterCodes.equals); + // for the ||||||| and ======== markers, add a comment for the first line, + // and then lex all subsequent lines up until the end of the conflict marker. + Debug.assert(ch === CharacterCodes.bar || ch === CharacterCodes.equals); classifyDisabledMergeCode(text, start, end); } } @@ -782,8 +782,8 @@ namespace ts { } function classifyDisabledMergeCode(text: string, start: number, end: number) { - // Classify the line that the ======= marker is on as a comment. Then just lex - // all further tokens and add them to the result. + // Classify the line that the ||||||| or ======= marker is on as a comment. + // Then just lex all further tokens and add them to the result. let i: number; for (i = start; i < end; i++) { if (isLineBreak(text.charCodeAt(i))) { From 2d60b2d1175d70542acb7029a3f80faa4c3e38ba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Kate=20Mih=C3=A1likov=C3=A1?= Date: Mon, 29 May 2017 13:41:28 +0200 Subject: [PATCH 42/56] Add tests and baselines --- .../unittests/services/colorization.ts | 44 +++++++++++++++++++ .../conflictMarkerDiff3Trivia1.errors.txt | 24 ++++++++++ .../reference/conflictMarkerDiff3Trivia1.js | 18 ++++++++ .../conflictMarkerDiff3Trivia2.errors.txt | 34 ++++++++++++++ .../reference/conflictMarkerDiff3Trivia2.js | 28 ++++++++++++ .../compiler/conflictMarkerDiff3Trivia1.ts | 9 ++++ .../compiler/conflictMarkerDiff3Trivia2.ts | 15 +++++++ .../fourslash/formatConflictDiff3Marker1.ts | 22 ++++++++++ ...ticClassificationsConflictDiff3Markers1.ts | 23 ++++++++++ ...ticClassificationsConflictDiff3Markers2.ts | 19 ++++++++ 10 files changed, 236 insertions(+) create mode 100644 tests/baselines/reference/conflictMarkerDiff3Trivia1.errors.txt create mode 100644 tests/baselines/reference/conflictMarkerDiff3Trivia1.js create mode 100644 tests/baselines/reference/conflictMarkerDiff3Trivia2.errors.txt create mode 100644 tests/baselines/reference/conflictMarkerDiff3Trivia2.js create mode 100644 tests/cases/compiler/conflictMarkerDiff3Trivia1.ts create mode 100644 tests/cases/compiler/conflictMarkerDiff3Trivia2.ts create mode 100644 tests/cases/fourslash/formatConflictDiff3Marker1.ts create mode 100644 tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers1.ts create mode 100644 tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers2.ts diff --git a/src/harness/unittests/services/colorization.ts b/src/harness/unittests/services/colorization.ts index fd7d932885a..3fed9ec6164 100644 --- a/src/harness/unittests/services/colorization.ts +++ b/src/harness/unittests/services/colorization.ts @@ -424,6 +424,50 @@ class D { }\r\n\ comment("=======\r\nclass D { }\r\n"), comment(">>>>>>> Branch - a"), finalEndOfLineState(ts.EndOfLineState.None)); + + testLexicalClassification( +"class C {\r\n\ +<<<<<<< HEAD\r\n\ + v = 1;\r\n\ +||||||| merged common ancestors\r\n\ + v = 3;\r\n\ +=======\r\n\ + v = 2;\r\n\ +>>>>>>> Branch - a\r\n\ +}", + ts.EndOfLineState.None, + keyword("class"), + identifier("C"), + punctuation("{"), + comment("<<<<<<< HEAD"), + identifier("v"), + operator("="), + numberLiteral("1"), + punctuation(";"), + comment("||||||| merged common ancestors\r\n v = 3;\r\n"), + comment("=======\r\n v = 2;\r\n"), + comment(">>>>>>> Branch - a"), + punctuation("}"), + finalEndOfLineState(ts.EndOfLineState.None)); + + testLexicalClassification( +"<<<<<<< HEAD\r\n\ +class C { }\r\n\ +||||||| merged common ancestors\r\n\ +class E { }\r\n\ +=======\r\n\ +class D { }\r\n\ +>>>>>>> Branch - a\r\n", + ts.EndOfLineState.None, + comment("<<<<<<< HEAD"), + keyword("class"), + identifier("C"), + punctuation("{"), + punctuation("}"), + comment("||||||| merged common ancestors\r\nclass E { }\r\n"), + comment("=======\r\nclass D { }\r\n"), + comment(">>>>>>> Branch - a"), + finalEndOfLineState(ts.EndOfLineState.None)); }); it("'of' keyword", function () { diff --git a/tests/baselines/reference/conflictMarkerDiff3Trivia1.errors.txt b/tests/baselines/reference/conflictMarkerDiff3Trivia1.errors.txt new file mode 100644 index 00000000000..b38e4e189ee --- /dev/null +++ b/tests/baselines/reference/conflictMarkerDiff3Trivia1.errors.txt @@ -0,0 +1,24 @@ +tests/cases/compiler/conflictMarkerDiff3Trivia1.ts(2,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia1.ts(4,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia1.ts(6,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia1.ts(8,1): error TS1185: Merge conflict marker encountered. + + +==== tests/cases/compiler/conflictMarkerDiff3Trivia1.ts (4 errors) ==== + class C { + <<<<<<< HEAD + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + v = 1; + ||||||| merged common ancestors + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + v = 3; + ======= + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + v = 2; + >>>>>>> Branch-a + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + } \ No newline at end of file diff --git a/tests/baselines/reference/conflictMarkerDiff3Trivia1.js b/tests/baselines/reference/conflictMarkerDiff3Trivia1.js new file mode 100644 index 00000000000..86cccd44e18 --- /dev/null +++ b/tests/baselines/reference/conflictMarkerDiff3Trivia1.js @@ -0,0 +1,18 @@ +//// [conflictMarkerDiff3Trivia1.ts] +class C { +<<<<<<< HEAD + v = 1; +||||||| merged common ancestors + v = 3; +======= + v = 2; +>>>>>>> Branch-a +} + +//// [conflictMarkerDiff3Trivia1.js] +var C = (function () { + function C() { + this.v = 1; + } + return C; +}()); diff --git a/tests/baselines/reference/conflictMarkerDiff3Trivia2.errors.txt b/tests/baselines/reference/conflictMarkerDiff3Trivia2.errors.txt new file mode 100644 index 00000000000..2e29826c43a --- /dev/null +++ b/tests/baselines/reference/conflictMarkerDiff3Trivia2.errors.txt @@ -0,0 +1,34 @@ +tests/cases/compiler/conflictMarkerDiff3Trivia2.ts(3,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia2.ts(4,6): error TS2304: Cannot find name 'a'. +tests/cases/compiler/conflictMarkerDiff3Trivia2.ts(6,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia2.ts(9,1): error TS1185: Merge conflict marker encountered. +tests/cases/compiler/conflictMarkerDiff3Trivia2.ts(12,1): error TS1185: Merge conflict marker encountered. + + +==== tests/cases/compiler/conflictMarkerDiff3Trivia2.ts (5 errors) ==== + class C { + foo() { + <<<<<<< B + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + a(); + ~ +!!! error TS2304: Cannot find name 'a'. + } + ||||||| merged common ancestors + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + c(); + } + ======= + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + b(); + } + >>>>>>> A + ~~~~~~~ +!!! error TS1185: Merge conflict marker encountered. + + public bar() { } + } + \ No newline at end of file diff --git a/tests/baselines/reference/conflictMarkerDiff3Trivia2.js b/tests/baselines/reference/conflictMarkerDiff3Trivia2.js new file mode 100644 index 00000000000..61a2273019b --- /dev/null +++ b/tests/baselines/reference/conflictMarkerDiff3Trivia2.js @@ -0,0 +1,28 @@ +//// [conflictMarkerDiff3Trivia2.ts] +class C { + foo() { +<<<<<<< B + a(); + } +||||||| merged common ancestors + c(); + } +======= + b(); + } +>>>>>>> A + + public bar() { } +} + + +//// [conflictMarkerDiff3Trivia2.js] +var C = (function () { + function C() { + } + C.prototype.foo = function () { + a(); + }; + C.prototype.bar = function () { }; + return C; +}()); diff --git a/tests/cases/compiler/conflictMarkerDiff3Trivia1.ts b/tests/cases/compiler/conflictMarkerDiff3Trivia1.ts new file mode 100644 index 00000000000..072cc4b9683 --- /dev/null +++ b/tests/cases/compiler/conflictMarkerDiff3Trivia1.ts @@ -0,0 +1,9 @@ +class C { +<<<<<<< HEAD + v = 1; +||||||| merged common ancestors + v = 3; +======= + v = 2; +>>>>>>> Branch-a +} \ No newline at end of file diff --git a/tests/cases/compiler/conflictMarkerDiff3Trivia2.ts b/tests/cases/compiler/conflictMarkerDiff3Trivia2.ts new file mode 100644 index 00000000000..023d425cd4d --- /dev/null +++ b/tests/cases/compiler/conflictMarkerDiff3Trivia2.ts @@ -0,0 +1,15 @@ +class C { + foo() { +<<<<<<< B + a(); + } +||||||| merged common ancestors + c(); + } +======= + b(); + } +>>>>>>> A + + public bar() { } +} diff --git a/tests/cases/fourslash/formatConflictDiff3Marker1.ts b/tests/cases/fourslash/formatConflictDiff3Marker1.ts new file mode 100644 index 00000000000..f6492a6f60c --- /dev/null +++ b/tests/cases/fourslash/formatConflictDiff3Marker1.ts @@ -0,0 +1,22 @@ +/// + +////class C { +////<<<<<<< HEAD +////v = 1; +////||||||| merged common ancestors +////v = 3; +////======= +////v = 2; +////>>>>>>> Branch - a +////} + +format.document(); +verify.currentFileContentIs("class C {\r\n\ +<<<<<<< HEAD\r\n\ + v = 1;\r\n\ +||||||| merged common ancestors\r\n\ +v = 3;\r\n\ +=======\r\n\ +v = 2;\r\n\ +>>>>>>> Branch - a\r\n\ +}"); \ No newline at end of file diff --git a/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers1.ts b/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers1.ts new file mode 100644 index 00000000000..669705307a9 --- /dev/null +++ b/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers1.ts @@ -0,0 +1,23 @@ +/// + +////class C { +////<<<<<<< HEAD +//// v = 1; +////||||||| merged common ancestors +//// v = 3; +////======= +//// v = 2; +////>>>>>>> Branch - a +////} + +const c = classification; +verify.syntacticClassificationsAre( + c.keyword("class"), c.className("C"), c.punctuation("{"), + c.comment("<<<<<<< HEAD"), + c.identifier("v"), c.operator("="), c.numericLiteral("1"), c.punctuation(";"), + c.comment("||||||| merged common ancestors"), + c.identifier("v"), c.punctuation("="), c.numericLiteral("3"), c.punctuation(";"), + c.comment("======="), + c.identifier("v"), c.punctuation("="), c.numericLiteral("2"), c.punctuation(";"), + c.comment(">>>>>>> Branch - a"), + c.punctuation("}")); \ No newline at end of file diff --git a/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers2.ts b/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers2.ts new file mode 100644 index 00000000000..17144397184 --- /dev/null +++ b/tests/cases/fourslash/syntacticClassificationsConflictDiff3Markers2.ts @@ -0,0 +1,19 @@ +/// + +////<<<<<<< HEAD +////class C { } +////||||||| merged common ancestors +////class E { } +////======= +////class D { } +////>>>>>>> Branch - a + +const c = classification; +verify.syntacticClassificationsAre( + c.comment("<<<<<<< HEAD"), + c.keyword("class"), c.className("C"), c.punctuation("{"), c.punctuation("}"), + c.comment("||||||| merged common ancestors"), + c.keyword("class"), c.identifier("E"), c.punctuation("{"), c.punctuation("}"), + c.comment("======="), + c.keyword("class"), c.identifier("D"), c.punctuation("{"), c.punctuation("}"), + c.comment(">>>>>>> Branch - a")); \ No newline at end of file From 05d3ff1823e7fe99e355de0d15517e681c37bdd7 Mon Sep 17 00:00:00 2001 From: Bill Ticehurst Date: Fri, 26 May 2017 13:56:57 -0700 Subject: [PATCH 43/56] Wrap npmLocation if needed --- src/server/typingsInstaller/nodeTypingsInstaller.ts | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/server/typingsInstaller/nodeTypingsInstaller.ts b/src/server/typingsInstaller/nodeTypingsInstaller.ts index 797962cba08..6a953cd6fce 100644 --- a/src/server/typingsInstaller/nodeTypingsInstaller.ts +++ b/src/server/typingsInstaller/nodeTypingsInstaller.ts @@ -85,6 +85,11 @@ namespace ts.server.typingsInstaller { throttleLimit, log); this.npmPath = npmLocation !== undefined ? npmLocation : getDefaultNPMLocation(process.argv[0]); + + // If the NPM path contains spaces and isn't wrapped in quotes, do so. + if (this.npmPath.indexOf(" ") !== -1 && this.npmPath[0] != `"`) { + this.npmPath = `"${this.npmPath}"`; + } if (this.log.isEnabled()) { this.log.writeLine(`Process id: ${process.pid}`); this.log.writeLine(`NPM location: ${this.npmPath} (explicit '${Arguments.NpmLocation}' ${npmLocation === undefined ? "not " : ""} provided)`); @@ -186,4 +191,4 @@ namespace ts.server.typingsInstaller { }); const installer = new NodeTypingsInstaller(globalTypingsCacheLocation, typingSafeListLocation, npmLocation, /*throttleLimit*/5, log); installer.listen(); -} \ No newline at end of file +} From 2e0eb265438e6619fd6b62c52df0f47a63e17810 Mon Sep 17 00:00:00 2001 From: Bill Ticehurst Date: Fri, 26 May 2017 14:02:18 -0700 Subject: [PATCH 44/56] Fix equals --- src/server/typingsInstaller/nodeTypingsInstaller.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/server/typingsInstaller/nodeTypingsInstaller.ts b/src/server/typingsInstaller/nodeTypingsInstaller.ts index 6a953cd6fce..de23b2649a6 100644 --- a/src/server/typingsInstaller/nodeTypingsInstaller.ts +++ b/src/server/typingsInstaller/nodeTypingsInstaller.ts @@ -87,7 +87,7 @@ namespace ts.server.typingsInstaller { this.npmPath = npmLocation !== undefined ? npmLocation : getDefaultNPMLocation(process.argv[0]); // If the NPM path contains spaces and isn't wrapped in quotes, do so. - if (this.npmPath.indexOf(" ") !== -1 && this.npmPath[0] != `"`) { + if (this.npmPath.indexOf(" ") !== -1 && this.npmPath[0] !== `"`) { this.npmPath = `"${this.npmPath}"`; } if (this.log.isEnabled()) { From b69afd16dc41d2a3cb3d12530f628389664504a9 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 30 May 2017 12:34:37 -0700 Subject: [PATCH 45/56] PR Feedback --- src/compiler/core.ts | 32 +++++-- src/compiler/factory.ts | 8 +- src/compiler/transformers/es2015.ts | 94 +++++++++++++++--- src/compiler/transformers/ts.ts | 30 +++--- src/compiler/utilities.ts | 144 ++++++---------------------- 5 files changed, 150 insertions(+), 158 deletions(-) diff --git a/src/compiler/core.ts b/src/compiler/core.ts index fec9b9092c2..2da7eaaa5af 100644 --- a/src/compiler/core.ts +++ b/src/compiler/core.ts @@ -740,6 +740,14 @@ namespace ts { return to; } + /** + * Gets the actual offset into an array for a relative offset. Negative offsets indicate a + * position offset from the end of the array. + */ + function toOffset(array: any[], offset: number) { + return offset < 0 ? array.length + offset : offset; + } + /** * Appends a range of value to an array, returning the array. * @@ -747,11 +755,19 @@ namespace ts { * is created if `value` was appended. * @param from The values to append to the array. If `from` is `undefined`, nothing is * appended. If an element of `from` is `undefined`, that element is not appended. + * @param start The offset in `from` at which to start copying values. + * @param end The offset in `from` at which to stop copying values (non-inclusive). */ - export function addRange(to: T[] | undefined, from: T[] | undefined): T[] | undefined { + export function addRange(to: T[] | undefined, from: T[] | undefined, start?: number, end?: number): T[] | undefined { if (from === undefined) return to; - for (const v of from) { - to = append(to, v); + if (to === undefined) return from.slice(start, end); + start = start === undefined ? 0 : toOffset(from, start); + end = end === undefined ? from.length : toOffset(from, end); + for (let i = start; i < end && i < from.length; i++) { + const v = from[i]; + if (v !== undefined) { + to.push(from[i]); + } } return to; } @@ -781,9 +797,13 @@ namespace ts { * A negative offset indicates the element should be retrieved from the end of the array. */ export function elementAt(array: T[] | undefined, offset: number): T | undefined { - return array && array.length > 0 && (offset < 0 ? ~offset : offset) < array.length - ? array[offset < 0 ? array.length + offset : offset] - : undefined; + if (array) { + offset = toOffset(array, offset); + if (offset < array.length) { + return array[offset]; + } + } + return undefined; } /** diff --git a/src/compiler/factory.ts b/src/compiler/factory.ts index 5d4457fdfd8..a3380d5cd9c 100644 --- a/src/compiler/factory.ts +++ b/src/compiler/factory.ts @@ -3736,7 +3736,7 @@ namespace ts { All = Parentheses | Assertions | PartiallyEmittedExpressions } - export type OuterExpression = ParenthesizedExpression | TypeAssertion | AsExpression | PartiallyEmittedExpression; + export type OuterExpression = ParenthesizedExpression | TypeAssertion | AsExpression | NonNullExpression | PartiallyEmittedExpression; export function isOuterExpression(node: Node, kinds = OuterExpressionKinds.All): node is OuterExpression { switch (node.kind) { @@ -3744,6 +3744,7 @@ namespace ts { return (kinds & OuterExpressionKinds.Parentheses) !== 0; case SyntaxKind.TypeAssertionExpression: case SyntaxKind.AsExpression: + case SyntaxKind.NonNullExpression: return (kinds & OuterExpressionKinds.Assertions) !== 0; case SyntaxKind.PartiallyEmittedExpression: return (kinds & OuterExpressionKinds.PartiallyEmittedExpressions) !== 0; @@ -3787,8 +3788,8 @@ namespace ts { export function skipAssertions(node: Expression): Expression; export function skipAssertions(node: Node): Node; export function skipAssertions(node: Node): Node { - while (isAssertionExpression(node)) { - node = (node).expression; + while (isAssertionExpression(node) || node.kind === SyntaxKind.NonNullExpression) { + node = (node).expression; } return node; @@ -3809,6 +3810,7 @@ namespace ts { case SyntaxKind.ParenthesizedExpression: return updateParen(outerExpression, expression); case SyntaxKind.TypeAssertionExpression: return updateTypeAssertion(outerExpression, outerExpression.type, expression); case SyntaxKind.AsExpression: return updateAsExpression(outerExpression, expression, outerExpression.type); + case SyntaxKind.NonNullExpression: return updateNonNullExpression(outerExpression, expression); case SyntaxKind.PartiallyEmittedExpression: return updatePartiallyEmittedExpression(outerExpression, expression); } } diff --git a/src/compiler/transformers/es2015.ts b/src/compiler/transformers/es2015.ts index 4b9c577805e..71a2fa0e2e0 100644 --- a/src/compiler/transformers/es2015.ts +++ b/src/compiler/transformers/es2015.ts @@ -339,6 +339,58 @@ namespace ts { && !(node).expression; } + function isClassLikeVariableStatement(node: Node) { + if (!isVariableStatement(node)) return false; + const variable = singleOrUndefined((node).declarationList.declarations); + return variable + && variable.initializer + && isIdentifier(variable.name) + && (isClassLike(variable.initializer) + || (isAssignmentExpression(variable.initializer) + && isIdentifier(variable.initializer.left) + && isClassLike(variable.initializer.right))); + } + + function isTypeScriptClassWrapper(node: Node) { + const call = tryCast(node, isCallExpression); + if (!call || isParseTreeNode(call) || + some(call.typeArguments) || + some(call.arguments)) { + return false; + } + + const func = tryCast(skipOuterExpressions(call.expression), isFunctionExpression); + if (!func || isParseTreeNode(func) || + some(func.typeParameters) || + some(func.parameters) || + func.type || + !func.body) { + return false; + } + + const statements = func.body.statements; + if (statements.length < 2) { + return false; + } + + const firstStatement = statements[0]; + if (isParseTreeNode(firstStatement) || + !isClassLike(firstStatement) && + !isClassLikeVariableStatement(firstStatement)) { + return false; + } + + const lastStatement = elementAt(statements, -1); + const returnStatement = tryCast(isVariableStatement(lastStatement) ? elementAt(statements, -2) : lastStatement, isReturnStatement); + if (!returnStatement || + !returnStatement.expression || + !isIdentifier(skipOuterExpressions(returnStatement.expression))) { + return false; + } + + return true; + } + function shouldVisitNode(node: Node): boolean { return (node.transformFlags & TransformFlags.ContainsES2015) !== 0 || convertedLoopState !== undefined @@ -3326,23 +3378,24 @@ namespace ts { // var C_1; // }()) // - const aliasAssignment = isAssignmentExpression(initializer) ? initializer : undefined; + const aliasAssignment = tryCast(initializer, isAssignmentExpression); // The underlying call (3) is another IIFE that may contain a '_super' argument. const call = cast(aliasAssignment ? skipOuterExpressions(aliasAssignment.right) : initializer, isCallExpression); const func = cast(skipOuterExpressions(call.expression), isFunctionExpression); - // When we extract the statements of the inner IIFE, we exclude the 'return' statement (4) - // as we already have one that has been introduced by the 'ts' transformer. - const funcStatements = func.body.statements.slice(0, -1); + const funcStatements = func.body.statements; + let classBodyStart = 0; + let classBodyEnd = -1; const statements: Statement[] = []; if (aliasAssignment) { // If we have a class alias assignment, we need to move it to the down-level constructor // function we generated for the class. - const hasExtendsCall = isExpressionStatement(funcStatements[0]); - if (hasExtendsCall) { - statements.push(funcStatements[0]); + const extendsCall = tryCast(funcStatements[classBodyStart], isExpressionStatement); + if (extendsCall) { + statements.push(extendsCall); + classBodyStart++; } // We reuse the comment and source-map positions from the original variable statement @@ -3359,25 +3412,37 @@ namespace ts { updateBinary(aliasAssignment, aliasAssignment.left, convertFunctionDeclarationToExpression( - cast(funcStatements[hasExtendsCall ? 1 : 0], isFunctionDeclaration) + cast(funcStatements[classBodyStart], isFunctionDeclaration) ) ) ) ]) ) ); - - addRange(statements, funcStatements.slice(hasExtendsCall ? 2 : 1)); - } - else { - addRange(statements, funcStatements); + classBodyStart++; } + // Find the trailing 'return' statement (4) + while (!isReturnStatement(elementAt(funcStatements, classBodyEnd))) { + classBodyEnd--; + } + + // When we extract the statements of the inner IIFE, we exclude the 'return' statement (4) + // as we already have one that has been introduced by the 'ts' transformer. + addRange(statements, funcStatements, classBodyStart, classBodyEnd); + + if (classBodyEnd < -1) { + // If there were any hoisted declarations following the return statement, we should + // append them. + addRange(statements, funcStatements, classBodyEnd + 1); + } + + // Add the remaining statements of the outer wrapper. addRange(statements, remainingStatements); // The 'es2015' class transform may add an end-of-declaration marker. If so we will add it // after the remaining statements from the 'ts' transformer. - addRange(statements, classStatements.slice(1)); + addRange(statements, classStatements, /*start*/ 1); // Recreate any outer parentheses or partially-emitted expressions to preserve source map // and comment locations. @@ -3952,7 +4017,6 @@ namespace ts { return false; } if (isClassElement(currentNode) && currentNode.parent === declaration) { - // we are in the class body, but we treat static fields as outside of the class body return true; } currentNode = currentNode.parent; diff --git a/src/compiler/transformers/ts.ts b/src/compiler/transformers/ts.ts index 876a7ff2d72..4fb21f7ec9e 100644 --- a/src/compiler/transformers/ts.ts +++ b/src/compiler/transformers/ts.ts @@ -19,10 +19,11 @@ namespace ts { } const enum ClassFacts { + None = 0, HasStaticInitializedProperties = 1 << 0, HasConstructorDecorators = 1 << 1, HasMemberDecorators = 1 << 2, - IsNamespaceExport = 1 << 3, + IsExportOfNamespace = 1 << 3, IsNamedExternalExport = 1 << 4, IsDefaultExternalExport = 1 << 5, HasExtendsClause = 1 << 6, @@ -31,7 +32,7 @@ namespace ts { HasAnyDecorators = HasConstructorDecorators | HasMemberDecorators, NeedsName = HasStaticInitializedProperties | HasMemberDecorators, MayNeedImmediatelyInvokedFunctionExpression = HasAnyDecorators | HasStaticInitializedProperties, - IsExported = IsNamespaceExport | IsDefaultExternalExport | IsNamedExternalExport, + IsExported = IsExportOfNamespace | IsDefaultExternalExport | IsNamedExternalExport, } export function transformTypeScript(context: TransformationContext) { @@ -519,14 +520,14 @@ namespace ts { } function getClassFacts(node: ClassDeclaration, staticProperties: PropertyDeclaration[]) { - let facts: ClassFacts = 0; + let facts = ClassFacts.None; if (some(staticProperties)) facts |= ClassFacts.HasStaticInitializedProperties; if (getClassExtendsHeritageClauseElement(node)) facts |= ClassFacts.HasExtendsClause; if (shouldEmitDecorateCallForClass(node)) facts |= ClassFacts.HasConstructorDecorators; if (childIsDecorated(node)) facts |= ClassFacts.HasMemberDecorators; - if (isNamespaceExport(node)) facts |= ClassFacts.IsNamespaceExport; - if ((facts & ClassFacts.IsExported) === 0 && isDefaultExternalModuleExport(node)) facts |= ClassFacts.IsDefaultExternalExport; - if ((facts & ClassFacts.IsExported) === 0 && isNamedExternalModuleExport(node)) facts |= ClassFacts.IsNamedExternalExport; + if (isExportOfNamespace(node)) facts |= ClassFacts.IsExportOfNamespace; + else if (isDefaultExternalModuleExport(node)) facts |= ClassFacts.IsDefaultExternalExport; + else if (isNamedExternalModuleExport(node)) facts |= ClassFacts.IsNamedExternalExport; if (languageVersion <= ScriptTarget.ES5 && (facts & ClassFacts.MayNeedImmediatelyInvokedFunctionExpression)) facts |= ClassFacts.UseImmediatelyInvokedFunctionExpression; return facts; } @@ -609,7 +610,7 @@ namespace ts { // If the class is exported as part of a TypeScript namespace, emit the namespace export. // Otherwise, if the class was exported at the top level and was decorated, emit an export // declaration or export default for the class. - if (facts & ClassFacts.IsNamespaceExport) { + if (facts & ClassFacts.IsExportOfNamespace) { addExportMemberAssignment(statements, node); } else if (facts & ClassFacts.UseImmediatelyInvokedFunctionExpression || facts & ClassFacts.HasConstructorDecorators) { @@ -672,11 +673,6 @@ namespace ts { /** * Transforms a decorated class declaration and appends the resulting statements. If * the class requires an alias to avoid issues with double-binding, the alias is returned. - * - * @param statements A statement list to which to add the declaration. - * @param node A ClassDeclaration node. - * @param name The name of the class. - * @param facts Precomputed facts about the clas. */ function createClassDeclarationHeadWithDecorators(node: ClassDeclaration, name: Identifier, facts: ClassFacts) { // When we emit an ES6 class that has a class decorator, we must tailor the @@ -2223,7 +2219,7 @@ namespace ts { /*type*/ undefined, visitFunctionBody(node.body, visitor, context) || createBlock([]) ); - if (isNamespaceExport(node)) { + if (isExportOfNamespace(node)) { const statements: Statement[] = [updated]; addExportMemberAssignment(statements, node); return statements; @@ -2316,7 +2312,7 @@ namespace ts { * - The node is exported from a TypeScript namespace. */ function visitVariableStatement(node: VariableStatement): Statement { - if (isNamespaceExport(node)) { + if (isExportOfNamespace(node)) { const variables = getInitializedVariables(node.declarationList); if (variables.length === 0) { // elide statement if there are no initialized variables. @@ -2620,7 +2616,7 @@ namespace ts { * or `exports.x`). */ function hasNamespaceQualifiedExportName(node: Node) { - return isNamespaceExport(node) + return isExportOfNamespace(node) || (isExternalModuleExport(node) && moduleKind !== ModuleKind.ES2015 && moduleKind !== ModuleKind.System); @@ -3062,7 +3058,7 @@ namespace ts { const moduleReference = createExpressionFromEntityName(node.moduleReference); setEmitFlags(moduleReference, EmitFlags.NoComments | EmitFlags.NoNestedComments); - if (isNamedExternalModuleExport(node) || !isNamespaceExport(node)) { + if (isNamedExternalModuleExport(node) || !isExportOfNamespace(node)) { // export var ${name} = ${moduleReference}; // var ${name} = ${moduleReference}; return setOriginalNode( @@ -3103,7 +3099,7 @@ namespace ts { * * @param node The node to test. */ - function isNamespaceExport(node: Node) { + function isExportOfNamespace(node: Node) { return currentNamespace !== undefined && hasModifier(node, ModifierFlags.Export); } diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index b5d3fe348d9..5ab6cb3c336 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -850,72 +850,10 @@ namespace ts { return node && (node.kind === SyntaxKind.GetAccessor || node.kind === SyntaxKind.SetAccessor); } - export function isClassLike(node: Node | undefined): node is ClassLikeDeclaration { + export function isClassLike(node: Node): node is ClassLikeDeclaration { return node && (node.kind === SyntaxKind.ClassDeclaration || node.kind === SyntaxKind.ClassExpression); } - export function isImmediatelyInvokedFunctionExpression(node: Node) { - if (!isCallExpression(node) || - some(node.typeArguments) || - some(node.arguments)) { - return false; - } - const expression = skipParentheses(node.expression); - if (!isFunctionExpression(expression) || - some(expression.typeParameters) || - some(expression.parameters) || - expression.type || - !expression.body) { - return false; - } - return true; - } - - export function isTypeScriptClassWrapper(node: Node) { - if (!isImmediatelyInvokedFunctionExpression(node) || - isParseTreeNode(node)) { - return false; - } - - const func = skipParentheses((node).expression); - if (isParseTreeNode(func)) { - return false; - } - - const statements = func.body.statements; - if (statements.length < 2) { - return false; - } - - const firstStatement = statements[0]; - if (isParseTreeNode(firstStatement) || - !isClassLike(firstStatement) && - !isClassLikeVariableStatement(firstStatement)) { - return false; - } - - const returnStatement = tryCast(elementAt(statements, isVariableStatement(lastOrUndefined(statements)) ? -2 : -1), isReturnStatement); - if (!isReturnStatement(returnStatement) || - !returnStatement.expression || - !isIdentifier(skipOuterExpressions(returnStatement.expression))) { - return false; - } - - return true; - } - - function isClassLikeVariableStatement(node: Node) { - if (!isVariableStatement(node)) return false; - const variable = singleOrUndefined((node).declarationList.declarations); - return variable - && variable.initializer - && isIdentifier(variable.name) - && (isClassLike(variable.initializer) - || (isAssignmentExpression(variable.initializer) - && isIdentifier(variable.initializer.left) - && isClassLike(variable.initializer.right))); - } - export function isExpressionStatement(node: Node): node is ExpressionStatement { return node.kind === SyntaxKind.ExpressionStatement; } @@ -3438,53 +3376,32 @@ namespace ts { /** * Formats an enum value as a string for debugging and debug assertions. */ - function formatEnum(value = 0, enumObject: any, isFlags: boolean, formatCache?: string[]) { - const cached = formatCache && formatCache[value]; - if (cached !== undefined) { - return cached; - } - const result = isFlags ? formatFlagsEnum(value, enumObject) : getEnumName(value, enumObject); - if (formatCache) { - formatCache[value] = result; - } - return result; - } - - /** - * Gets the name for an enum value for debugging and debug assertions. - */ - function getEnumName(value: number, enumObject: any) { - for (const name in enumObject) { - if (enumObject[name] === value) { - return name; - } - } - return value.toString(); - } - - /** - * Formats the bitwise flag values of an enum value for debugging and debug assertions. - */ - function formatFlagsEnum(value: number, enumObject: any) { + function formatEnum(value = 0, enumObject: any, isFlags?: boolean) { const members = getEnumMembers(enumObject); - let result = ""; if (value === 0) { return members.length > 0 && members[0][0] === 0 ? members[0][1] : "0"; } - - let remainingFlags = value; - for (let i = members.length - 1; i >= 0 && remainingFlags !== 0; i--) { - const [enumValue, enumName] = members[i]; - if (enumValue !== 0 && (remainingFlags & enumValue) === enumValue) { - remainingFlags &= ~enumValue; - result = `${enumName}${result ? ", " : ""}${result}`; + if (isFlags) { + let result = ""; + let remainingFlags = value; + for (let i = members.length - 1; i >= 0 && remainingFlags !== 0; i--) { + const [enumValue, enumName] = members[i]; + if (enumValue !== 0 && (remainingFlags & enumValue) === enumValue) { + remainingFlags &= ~enumValue; + result = `${enumName}${result ? ", " : ""}${result}`; + } + } + if (remainingFlags === 0) { + return result; } } - - if (remainingFlags === 0) { - return result; + else { + for (const [enumValue, enumName] of members) { + if (enumValue === value) { + return enumName; + } + } } - return value.toString(); } @@ -3500,39 +3417,32 @@ namespace ts { return stableSort(result, (x, y) => compareValues(x[0], y[0])); } - const syntaxKindCache: string[] = []; export function formatSyntaxKind(kind: SyntaxKind): string { - return formatEnum(kind, (ts).SyntaxKind, /*isFlags*/ false, syntaxKindCache); + return formatEnum(kind, (ts).SyntaxKind, /*isFlags*/ false); } - const modifierFlagsCache: string[] = []; export function formatModifierFlags(flags: ModifierFlags): string { - return formatEnum(flags, (ts).ModifierFlags, /*isFlags*/ true, modifierFlagsCache); + return formatEnum(flags, (ts).ModifierFlags, /*isFlags*/ true); } - const transformFlagsCache: string[] = []; export function formatTransformFlags(flags: TransformFlags): string { - return formatEnum(flags, (ts).TransformFlags, /*isFlags*/ true, transformFlagsCache); + return formatEnum(flags, (ts).TransformFlags, /*isFlags*/ true); } - const emitFlagsCache: string[] = []; export function formatEmitFlags(flags: EmitFlags): string { - return formatEnum(flags, (ts).EmitFlags, /*isFlags*/ true, emitFlagsCache); + return formatEnum(flags, (ts).EmitFlags, /*isFlags*/ true); } - const symbolFlagsCache: string[] = []; export function formatSymbolFlags(flags: SymbolFlags): string { - return formatEnum(flags, (ts).SymbolFlags, /*isFlags*/ true, symbolFlagsCache); + return formatEnum(flags, (ts).SymbolFlags, /*isFlags*/ true); } - const typeFlagsCache: string[] = []; export function formatTypeFlags(flags: TypeFlags): string { - return formatEnum(flags, (ts).TypeFlags, /*isFlags*/ true, typeFlagsCache); + return formatEnum(flags, (ts).TypeFlags, /*isFlags*/ true); } - const objectFlagsCache: string[] = []; export function formatObjectFlags(flags: ObjectFlags): string { - return formatEnum(flags, (ts).ObjectFlags, /*isFlags*/ true, objectFlagsCache); + return formatEnum(flags, (ts).ObjectFlags, /*isFlags*/ true); } export function getRangePos(range: TextRange | undefined) { From 2dd6627022c3d54b73d0d415971a451b14e2d8a1 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Tue, 30 May 2017 13:32:46 -0700 Subject: [PATCH 46/56] Report jsdoc syntax errors when checkJs is on --- src/compiler/parser.ts | 6 ++++++ src/compiler/program.ts | 3 +++ src/compiler/types.ts | 13 ++++++++----- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src/compiler/parser.ts b/src/compiler/parser.ts index 2d0a4b66a1a..51c9375c291 100644 --- a/src/compiler/parser.ts +++ b/src/compiler/parser.ts @@ -6322,6 +6322,12 @@ namespace ts { comment.parent = parent; } + if (isInJavaScriptFile(parent)) { + if (!sourceFile.jsDocDiagnostics) { + sourceFile.jsDocDiagnostics = []; + } + sourceFile.jsDocDiagnostics.push(...parseDiagnostics); + } currentToken = saveToken; parseDiagnostics.length = saveParseDiagnosticsLength; parseErrorBeforeNextFinishedNode = saveParseErrorBeforeNextFinishedNode; diff --git a/src/compiler/program.ts b/src/compiler/program.ts index dd293727b4a..e69a89cc618 100644 --- a/src/compiler/program.ts +++ b/src/compiler/program.ts @@ -1021,6 +1021,9 @@ namespace ts { if (isSourceFileJavaScript(sourceFile)) { if (!sourceFile.additionalSyntacticDiagnostics) { sourceFile.additionalSyntacticDiagnostics = getJavaScriptSyntacticDiagnosticsForFile(sourceFile); + if (isCheckJsEnabledForFile(sourceFile, options)) { + sourceFile.additionalSyntacticDiagnostics = concatenate(sourceFile.additionalSyntacticDiagnostics, sourceFile.jsDocDiagnostics); + } } return concatenate(sourceFile.additionalSyntacticDiagnostics, sourceFile.parseDiagnostics); } diff --git a/src/compiler/types.ts b/src/compiler/types.ts index 6f602ff23af..aaa790b6d13 100644 --- a/src/compiler/types.ts +++ b/src/compiler/types.ts @@ -2312,16 +2312,19 @@ namespace ts { /* @internal */ identifierCount: number; /* @internal */ symbolCount: number; - // File level diagnostics reported by the parser (includes diagnostics about /// references + // File-level diagnostics reported by the parser (includes diagnostics about /// references // as well as code diagnostics). /* @internal */ parseDiagnostics: Diagnostic[]; - // Stores additional file level diagnostics reported by the program - /* @internal */ additionalSyntacticDiagnostics?: Diagnostic[]; - - // File level diagnostics reported by the binder. + // File-level diagnostics reported by the binder. /* @internal */ bindDiagnostics: Diagnostic[]; + // File-level JSDoc diagnostics reported by the JSDoc parser + /* @internal */ jsDocDiagnostics?: Diagnostic[]; + + // Stores additional file-level diagnostics reported by the program + /* @internal */ additionalSyntacticDiagnostics?: Diagnostic[]; + // Stores a line map for the file. // This field should never be used directly to obtain line map, use getLineMap function instead. /* @internal */ lineMap: number[]; From 41e134529a6797904b0f8d39685cfdd2f4aea7e0 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Tue, 30 May 2017 13:33:13 -0700 Subject: [PATCH 47/56] Test reporting jsdoc syntax errors --- .../reference/syntaxErrors.errors.txt | 31 +++++++++++++++++++ tests/cases/conformance/jsdoc/syntaxErrors.ts | 20 ++++++++++++ 2 files changed, 51 insertions(+) create mode 100644 tests/baselines/reference/syntaxErrors.errors.txt create mode 100644 tests/cases/conformance/jsdoc/syntaxErrors.ts diff --git a/tests/baselines/reference/syntaxErrors.errors.txt b/tests/baselines/reference/syntaxErrors.errors.txt new file mode 100644 index 00000000000..8e3005891a5 --- /dev/null +++ b/tests/baselines/reference/syntaxErrors.errors.txt @@ -0,0 +1,31 @@ +tests/cases/conformance/jsdoc/foo.js(2,15): error TS1005: '}' expected. +tests/cases/conformance/jsdoc/foo.js(3,19): error TS1005: '}' expected. +tests/cases/conformance/jsdoc/foo.js(4,18): error TS1003: Identifier expected. +tests/cases/conformance/jsdoc/foo.js(4,19): error TS1005: '}' expected. + + +==== tests/cases/conformance/jsdoc/foo.js (4 errors) ==== + /** + * @param {(x)=>void} x + ~~ +!!! error TS1005: '}' expected. + * @param {typeof String} y + ~~~~~~ +!!! error TS1005: '}' expected. + * @param {string & number} z + +!!! error TS1003: Identifier expected. + ~ +!!! error TS1005: '}' expected. + **/ + function foo(x, y, z) { } + +==== tests/cases/conformance/jsdoc/skipped.js (0 errors) ==== + // @ts-nocheck + /** + * @param {(x)=>void} x + * @param {typeof String} y + * @param {string & number} z + **/ + function bar(x, y, z) { } + \ No newline at end of file diff --git a/tests/cases/conformance/jsdoc/syntaxErrors.ts b/tests/cases/conformance/jsdoc/syntaxErrors.ts new file mode 100644 index 00000000000..4f9024810dd --- /dev/null +++ b/tests/cases/conformance/jsdoc/syntaxErrors.ts @@ -0,0 +1,20 @@ +// @checkJs: true +// @allowJs: true +// @noEmit: true + +// @Filename: foo.js +/** + * @param {(x)=>void} x + * @param {typeof String} y + * @param {string & number} z + **/ +function foo(x, y, z) { } + +// @Filename: skipped.js +// @ts-nocheck +/** + * @param {(x)=>void} x + * @param {typeof String} y + * @param {string & number} z + **/ +function bar(x, y, z) { } From 1459395c99863b3f57e6d71b350bad1e2111c177 Mon Sep 17 00:00:00 2001 From: Kanchalai Tanglertsampan Date: Tue, 30 May 2017 13:47:36 -0700 Subject: [PATCH 48/56] Update fail symbol baselines --- .../reference/checkJsdocTypeTag1.symbols | 25 +++++++++++++------ 1 file changed, 17 insertions(+), 8 deletions(-) diff --git a/tests/baselines/reference/checkJsdocTypeTag1.symbols b/tests/baselines/reference/checkJsdocTypeTag1.symbols index 39848ff50a8..fff51499bc4 100644 --- a/tests/baselines/reference/checkJsdocTypeTag1.symbols +++ b/tests/baselines/reference/checkJsdocTypeTag1.symbols @@ -31,21 +31,30 @@ const x = (a) => a + 1; x(1); >x : Symbol(x, Decl(0.js, 16, 5)) +/** @type {function} */ +const y = (a) => a + 1; +>y : Symbol(y, Decl(0.js, 20, 5)) +>a : Symbol(a, Decl(0.js, 20, 11)) +>a : Symbol(a, Decl(0.js, 20, 11)) + +x(1); +>x : Symbol(x, Decl(0.js, 16, 5)) + /** @type {function (number)} */ const x1 = (a) => a + 1; ->x1 : Symbol(x1, Decl(0.js, 20, 5)) ->a : Symbol(a, Decl(0.js, 20, 12)) ->a : Symbol(a, Decl(0.js, 20, 12)) +>x1 : Symbol(x1, Decl(0.js, 24, 5)) +>a : Symbol(a, Decl(0.js, 24, 12)) +>a : Symbol(a, Decl(0.js, 24, 12)) x1(0); ->x1 : Symbol(x1, Decl(0.js, 20, 5)) +>x1 : Symbol(x1, Decl(0.js, 24, 5)) /** @type {function (number): number} */ const x2 = (a) => a + 1; ->x2 : Symbol(x2, Decl(0.js, 24, 5)) ->a : Symbol(a, Decl(0.js, 24, 12)) ->a : Symbol(a, Decl(0.js, 24, 12)) +>x2 : Symbol(x2, Decl(0.js, 28, 5)) +>a : Symbol(a, Decl(0.js, 28, 12)) +>a : Symbol(a, Decl(0.js, 28, 12)) x2(0); ->x2 : Symbol(x2, Decl(0.js, 24, 5)) +>x2 : Symbol(x2, Decl(0.js, 28, 5)) From 3029313f3292823a39b39abb57d598cc6c6267e8 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 30 May 2017 15:14:52 -0700 Subject: [PATCH 49/56] Fix issue with 'for await' over a union type --- src/compiler/checker.ts | 124 +++++++++--------- tests/baselines/reference/forAwaitForUnion.js | 11 ++ .../reference/forAwaitForUnion.symbols | 15 +++ .../reference/forAwaitForUnion.types | 15 +++ tests/cases/compiler/forAwaitForUnion.ts | 6 + 5 files changed, 107 insertions(+), 64 deletions(-) create mode 100644 tests/baselines/reference/forAwaitForUnion.js create mode 100644 tests/baselines/reference/forAwaitForUnion.symbols create mode 100644 tests/baselines/reference/forAwaitForUnion.types create mode 100644 tests/cases/compiler/forAwaitForUnion.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 9ff1c4b41b9..7ef6aa6217d 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -4117,7 +4117,7 @@ namespace ts { // This elementType will be used if the specific property corresponding to this index is not // present (aka the tuple element property). This call also checks that the parentType is in // fact an iterable or array (depending on target language). - const elementType = checkIteratedTypeOrElementType(parentType, pattern, /*allowStringInput*/ false, /*allowAsyncIterable*/ false); + const elementType = checkIteratedTypeOrElementType(parentType, pattern, /*allowStringInput*/ false, /*allowAsyncIterables*/ false); if (declaration.dotDotDotToken) { // Rest element has an array type with the same element type as the parent type type = createArrayType(elementType); @@ -10888,12 +10888,12 @@ namespace ts { function getTypeOfDestructuredArrayElement(type: Type, index: number) { return isTupleLikeType(type) && getTypeOfPropertyOfType(type, "" + index) || - checkIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterable*/ false) || + checkIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterables*/ false) || unknownType; } function getTypeOfDestructuredSpreadExpression(type: Type) { - return createArrayType(checkIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterable*/ false) || unknownType); + return createArrayType(checkIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterables*/ false) || unknownType); } function getAssignedTypeOfBinaryExpression(node: BinaryExpression): Type { @@ -12867,7 +12867,7 @@ namespace ts { const index = indexOf(arrayLiteral.elements, node); return getTypeOfPropertyOfContextualType(type, "" + index) || getIndexTypeOfContextualType(type, IndexKind.Number) - || getIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterable*/ false, /*checkAssignability*/ false); + || getIteratedTypeOrElementType(type, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterables*/ false, /*checkAssignability*/ false); } return undefined; } @@ -13105,7 +13105,7 @@ namespace ts { } const arrayOrIterableType = checkExpression(node.expression, checkMode); - return checkIteratedTypeOrElementType(arrayOrIterableType, node.expression, /*allowStringInput*/ false, /*allowAsyncIterable*/ false); + return checkIteratedTypeOrElementType(arrayOrIterableType, node.expression, /*allowStringInput*/ false, /*allowAsyncIterables*/ false); } function hasDefaultValue(node: BindingElement | Expression): boolean { @@ -13134,7 +13134,7 @@ namespace ts { // if there is no index type / iterated type. const restArrayType = checkExpression((e).expression, checkMode); const restElementType = getIndexTypeOfType(restArrayType, IndexKind.Number) || - getIteratedTypeOrElementType(restArrayType, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterable*/ false, /*checkAssignability*/ false); + getIteratedTypeOrElementType(restArrayType, /*errorNode*/ undefined, /*allowStringInput*/ false, /*allowAsyncIterables*/ false, /*checkAssignability*/ false); if (restElementType) { elementTypes.push(restElementType); } @@ -16987,7 +16987,7 @@ namespace ts { // This elementType will be used if the specific property corresponding to this index is not // present (aka the tuple element property). This call also checks that the parentType is in // fact an iterable or array (depending on target language). - const elementType = checkIteratedTypeOrElementType(sourceType, node, /*allowStringInput*/ false, /*allowAsyncIterable*/ false) || unknownType; + const elementType = checkIteratedTypeOrElementType(sourceType, node, /*allowStringInput*/ false, /*allowAsyncIterables*/ false) || unknownType; const elements = node.elements; for (let i = 0; i < elements.length; i++) { checkArrayLiteralDestructuringElementAssignment(node, sourceType, i, elementType, checkMode); @@ -20131,12 +20131,12 @@ namespace ts { return checkIteratedTypeOrElementType(expressionType, rhsExpression, /*allowStringInput*/ true, awaitModifier !== undefined); } - function checkIteratedTypeOrElementType(inputType: Type, errorNode: Node, allowStringInput: boolean, allowAsyncIterable: boolean): Type { + function checkIteratedTypeOrElementType(inputType: Type, errorNode: Node, allowStringInput: boolean, allowAsyncIterables: boolean): Type { if (isTypeAny(inputType)) { return inputType; } - return getIteratedTypeOrElementType(inputType, errorNode, allowStringInput, allowAsyncIterable, /*checkAssignability*/ true) || anyType; + return getIteratedTypeOrElementType(inputType, errorNode, allowStringInput, allowAsyncIterables, /*checkAssignability*/ true) || anyType; } /** @@ -20144,16 +20144,16 @@ namespace ts { * we want to get the iterated type of an iterable for ES2015 or later, or the iterated type * of a iterable (if defined globally) or element type of an array like for ES2015 or earlier. */ - function getIteratedTypeOrElementType(inputType: Type, errorNode: Node, allowStringInput: boolean, allowAsyncIterable: boolean, checkAssignability: boolean): Type { + function getIteratedTypeOrElementType(inputType: Type, errorNode: Node, allowStringInput: boolean, allowAsyncIterables: boolean, checkAssignability: boolean): Type { const uplevelIteration = languageVersion >= ScriptTarget.ES2015; const downlevelIteration = !uplevelIteration && compilerOptions.downlevelIteration; // Get the iterated type of an `Iterable` or `IterableIterator` only in ES2015 // or higher, when inside of an async generator or for-await-if, or when // downlevelIteration is requested. - if (uplevelIteration || downlevelIteration || allowAsyncIterable) { + if (uplevelIteration || downlevelIteration || allowAsyncIterables) { // We only report errors for an invalid iterable type in ES2015 or higher. - const iteratedType = getIteratedTypeOfIterable(inputType, uplevelIteration ? errorNode : undefined, allowAsyncIterable, allowAsyncIterable, checkAssignability); + const iteratedType = getIteratedTypeOfIterable(inputType, uplevelIteration ? errorNode : undefined, allowAsyncIterables, /*allowSyncIterables*/ true, checkAssignability); if (iteratedType || uplevelIteration) { return iteratedType; } @@ -20267,79 +20267,75 @@ namespace ts { * For a **for-await-of** statement or a `yield*` in an async generator we will look for * the `[Symbol.asyncIterator]()` method first, and then the `[Symbol.iterator]()` method. */ - function getIteratedTypeOfIterable(type: Type, errorNode: Node | undefined, isAsyncIterable: boolean, allowNonAsyncIterables: boolean, checkAssignability: boolean): Type | undefined { + function getIteratedTypeOfIterable(type: Type, errorNode: Node | undefined, allowAsyncIterables: boolean, allowSyncIterables: boolean, checkAssignability: boolean): Type | undefined { if (isTypeAny(type)) { return undefined; } - const typeAsIterable = type; - if (isAsyncIterable ? typeAsIterable.iteratedTypeOfAsyncIterable : typeAsIterable.iteratedTypeOfIterable) { - return isAsyncIterable ? typeAsIterable.iteratedTypeOfAsyncIterable : typeAsIterable.iteratedTypeOfIterable; - } + return mapType(type, getIteratedType); - if (isAsyncIterable) { - // As an optimization, if the type is an instantiation of the global `AsyncIterable` - // or the global `AsyncIterableIterator` then just grab its type argument. - if (isReferenceToType(type, getGlobalAsyncIterableType(/*reportErrors*/ false)) || - isReferenceToType(type, getGlobalAsyncIterableIteratorType(/*reportErrors*/ false))) { - return typeAsIterable.iteratedTypeOfAsyncIterable = (type).typeArguments[0]; + function getIteratedType(type: Type) { + const typeAsIterable = type; + if (allowAsyncIterables) { + if (typeAsIterable.iteratedTypeOfAsyncIterable) { + return typeAsIterable.iteratedTypeOfAsyncIterable; + } + + // As an optimization, if the type is an instantiation of the global `AsyncIterable` + // or the global `AsyncIterableIterator` then just grab its type argument. + if (isReferenceToType(type, getGlobalAsyncIterableType(/*reportErrors*/ false)) || + isReferenceToType(type, getGlobalAsyncIterableIteratorType(/*reportErrors*/ false))) { + return typeAsIterable.iteratedTypeOfAsyncIterable = (type).typeArguments[0]; + } } - } - if (!isAsyncIterable || allowNonAsyncIterables) { - // As an optimization, if the type is an instantiation of the global `Iterable` or - // `IterableIterator` then just grab its type argument. - if (isReferenceToType(type, getGlobalIterableType(/*reportErrors*/ false)) || - isReferenceToType(type, getGlobalIterableIteratorType(/*reportErrors*/ false))) { - return isAsyncIterable - ? typeAsIterable.iteratedTypeOfAsyncIterable = (type).typeArguments[0] - : typeAsIterable.iteratedTypeOfIterable = (type).typeArguments[0]; + if (allowSyncIterables) { + if (typeAsIterable.iteratedTypeOfIterable) { + return typeAsIterable.iteratedTypeOfIterable; + } + + // As an optimization, if the type is an instantiation of the global `Iterable` or + // `IterableIterator` then just grab its type argument. + if (isReferenceToType(type, getGlobalIterableType(/*reportErrors*/ false)) || + isReferenceToType(type, getGlobalIterableIteratorType(/*reportErrors*/ false))) { + return typeAsIterable.iteratedTypeOfIterable = (type).typeArguments[0]; + } } - } - let iteratorMethodSignatures: Signature[]; - let isNonAsyncIterable = false; - if (isAsyncIterable) { - const iteratorMethod = getTypeOfPropertyOfType(type, getPropertyNameForKnownSymbolName("asyncIterator")); - if (isTypeAny(iteratorMethod)) { + const asyncMethodType = allowAsyncIterables && getTypeOfPropertyOfType(type, getPropertyNameForKnownSymbolName("asyncIterator")); + const methodType = asyncMethodType || (allowSyncIterables && getTypeOfPropertyOfType(type, getPropertyNameForKnownSymbolName("iterator"))); + if (isTypeAny(methodType)) { return undefined; } - iteratorMethodSignatures = iteratorMethod && getSignaturesOfType(iteratorMethod, SignatureKind.Call); - } - if (!isAsyncIterable || (allowNonAsyncIterables && !some(iteratorMethodSignatures))) { - const iteratorMethod = getTypeOfPropertyOfType(type, getPropertyNameForKnownSymbolName("iterator")); - if (isTypeAny(iteratorMethod)) { + const signatures = methodType && getSignaturesOfType(methodType, SignatureKind.Call); + if (!some(signatures)) { + if (errorNode) { + error(errorNode, + allowAsyncIterables + ? Diagnostics.Type_must_have_a_Symbol_asyncIterator_method_that_returns_an_async_iterator + : Diagnostics.Type_must_have_a_Symbol_iterator_method_that_returns_an_iterator); + // only report on the first error + errorNode = undefined; + } return undefined; } - iteratorMethodSignatures = iteratorMethod && getSignaturesOfType(iteratorMethod, SignatureKind.Call); - isNonAsyncIterable = true; - } - if (some(iteratorMethodSignatures)) { - const iteratorMethodReturnType = getUnionType(map(iteratorMethodSignatures, getReturnTypeOfSignature), /*subtypeReduction*/ true); - const iteratedType = getIteratedTypeOfIterator(iteratorMethodReturnType, errorNode, /*isAsyncIterator*/ !isNonAsyncIterable); + const returnType = getUnionType(map(signatures, getReturnTypeOfSignature), /*subtypeReduction*/ true); + const iteratedType = getIteratedTypeOfIterator(returnType, errorNode, /*isAsyncIterator*/ !!asyncMethodType); if (checkAssignability && errorNode && iteratedType) { // If `checkAssignability` was specified, we were called from // `checkIteratedTypeOrElementType`. As such, we need to validate that // the type passed in is actually an Iterable. - checkTypeAssignableTo(type, isNonAsyncIterable - ? createIterableType(iteratedType) - : createAsyncIterableType(iteratedType), errorNode); + checkTypeAssignableTo(type, asyncMethodType + ? createAsyncIterableType(iteratedType) + : createIterableType(iteratedType), errorNode); } - return isAsyncIterable + + return asyncMethodType ? typeAsIterable.iteratedTypeOfAsyncIterable = iteratedType : typeAsIterable.iteratedTypeOfIterable = iteratedType; } - - if (errorNode) { - error(errorNode, - isAsyncIterable - ? Diagnostics.Type_must_have_a_Symbol_asyncIterator_method_that_returns_an_async_iterator - : Diagnostics.Type_must_have_a_Symbol_iterator_method_that_returns_an_iterator); - } - - return undefined; } /** @@ -20439,7 +20435,7 @@ namespace ts { return undefined; } - return getIteratedTypeOfIterable(returnType, /*errorNode*/ undefined, isAsyncGenerator, /*allowNonAsyncIterables*/ false, /*checkAssignability*/ false) + return getIteratedTypeOfIterable(returnType, /*errorNode*/ undefined, /*allowAsyncIterables*/ isAsyncGenerator, /*allowSyncIterables*/ !isAsyncGenerator, /*checkAssignability*/ false) || getIteratedTypeOfIterator(returnType, /*errorNode*/ undefined, isAsyncGenerator); } @@ -22649,7 +22645,7 @@ namespace ts { Debug.assert(expr.parent.kind === SyntaxKind.ArrayLiteralExpression); // [{ property1: p1, property2 }] = elems; const typeOfArrayLiteral = getTypeOfArrayLiteralOrObjectLiteralDestructuringAssignment(expr.parent); - const elementType = checkIteratedTypeOrElementType(typeOfArrayLiteral || unknownType, expr.parent, /*allowStringInput*/ false, /*allowAsyncIterable*/ false) || unknownType; + const elementType = checkIteratedTypeOrElementType(typeOfArrayLiteral || unknownType, expr.parent, /*allowStringInput*/ false, /*allowAsyncIterables*/ false) || unknownType; return checkArrayLiteralDestructuringElementAssignment(expr.parent, typeOfArrayLiteral, indexOf((expr.parent).elements, expr), elementType || unknownType); } diff --git a/tests/baselines/reference/forAwaitForUnion.js b/tests/baselines/reference/forAwaitForUnion.js new file mode 100644 index 00000000000..e0a4b9ebf82 --- /dev/null +++ b/tests/baselines/reference/forAwaitForUnion.js @@ -0,0 +1,11 @@ +//// [forAwaitForUnion.ts] +async function f(source: Iterable | AsyncIterable) { + for await (const x of source) { + } +} + +//// [forAwaitForUnion.js] +async function f(source) { + for await (const x of source) { + } +} diff --git a/tests/baselines/reference/forAwaitForUnion.symbols b/tests/baselines/reference/forAwaitForUnion.symbols new file mode 100644 index 00000000000..8b31ea48684 --- /dev/null +++ b/tests/baselines/reference/forAwaitForUnion.symbols @@ -0,0 +1,15 @@ +=== tests/cases/compiler/forAwaitForUnion.ts === +async function f(source: Iterable | AsyncIterable) { +>f : Symbol(f, Decl(forAwaitForUnion.ts, 0, 0)) +>T : Symbol(T, Decl(forAwaitForUnion.ts, 0, 17)) +>source : Symbol(source, Decl(forAwaitForUnion.ts, 0, 20)) +>Iterable : Symbol(Iterable, Decl(lib.es2015.iterable.d.ts, --, --)) +>T : Symbol(T, Decl(forAwaitForUnion.ts, 0, 17)) +>AsyncIterable : Symbol(AsyncIterable, Decl(lib.esnext.asynciterable.d.ts, --, --)) +>T : Symbol(T, Decl(forAwaitForUnion.ts, 0, 17)) + + for await (const x of source) { +>x : Symbol(x, Decl(forAwaitForUnion.ts, 1, 20)) +>source : Symbol(source, Decl(forAwaitForUnion.ts, 0, 20)) + } +} diff --git a/tests/baselines/reference/forAwaitForUnion.types b/tests/baselines/reference/forAwaitForUnion.types new file mode 100644 index 00000000000..715fd120ca8 --- /dev/null +++ b/tests/baselines/reference/forAwaitForUnion.types @@ -0,0 +1,15 @@ +=== tests/cases/compiler/forAwaitForUnion.ts === +async function f(source: Iterable | AsyncIterable) { +>f : (source: Iterable | AsyncIterable) => Promise +>T : T +>source : Iterable | AsyncIterable +>Iterable : Iterable +>T : T +>AsyncIterable : AsyncIterable +>T : T + + for await (const x of source) { +>x : T +>source : Iterable | AsyncIterable + } +} diff --git a/tests/cases/compiler/forAwaitForUnion.ts b/tests/cases/compiler/forAwaitForUnion.ts new file mode 100644 index 00000000000..65e08ab77a9 --- /dev/null +++ b/tests/cases/compiler/forAwaitForUnion.ts @@ -0,0 +1,6 @@ +// @target: esnext +// @lib: esnext +async function f(source: Iterable | AsyncIterable) { + for await (const x of source) { + } +} \ No newline at end of file From 423d8a077dfffc7666adc6f7de104ac6df9f75b3 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 30 May 2017 15:29:31 -0700 Subject: [PATCH 50/56] PR feedback --- src/compiler/transformers/es2015.ts | 5 ++++- src/compiler/transformers/ts.ts | 11 +++++++++++ 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/src/compiler/transformers/es2015.ts b/src/compiler/transformers/es2015.ts index 71a2fa0e2e0..9dba20be285 100644 --- a/src/compiler/transformers/es2015.ts +++ b/src/compiler/transformers/es2015.ts @@ -3360,10 +3360,13 @@ namespace ts { const classStatements = visitNodes(body.statements, visitor, isStatement, 0, 1); const remainingStatements = visitNodes(body.statements, visitor, isStatement, 1, body.statements.length - 1); const varStatement = cast(firstOrUndefined(classStatements), isVariableStatement); + + // We know there is only one variable declaration here as we verified this in an + // earlier call to isTypeScriptClassWrapper const variable = varStatement.declarationList.declarations[0]; const initializer = skipOuterExpressions(variable.initializer); - // Under certain conditions, the 'ts' transformer may may introduce a class alias, which + // Under certain conditions, the 'ts' transformer may introduce a class alias, which // we see as an assignment, for example: // // (function () { diff --git a/src/compiler/transformers/ts.ts b/src/compiler/transformers/ts.ts index 4fb21f7ec9e..e8a2a2f00c7 100644 --- a/src/compiler/transformers/ts.ts +++ b/src/compiler/transformers/ts.ts @@ -573,6 +573,17 @@ namespace ts { addConstructorDecorationStatement(statements, node); if (facts & ClassFacts.UseImmediatelyInvokedFunctionExpression) { + // When we emit a TypeScript class down to ES5, we must wrap it in an IIFE so that the + // 'es2015' transformer can properly nest static initializers and decorators. The result + // looks something like: + // + // var C = function () { + // class C { + // } + // C.static_prop = 1; + // return C; + // }(); + // const closingBraceLocation = createTokenRange(skipTrivia(currentSourceFile.text, node.members.end), SyntaxKind.CloseBraceToken); const localName = getInternalName(node); From f69a1c16022d06e4d67129af9e7edb3b0947359a Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 30 May 2017 16:50:24 -0700 Subject: [PATCH 51/56] Update build scripts for npm5 --- .travis.yml | 4 ++-- jenkins.sh | 6 +++--- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 7231d89d354..33e44a349aa 100644 --- a/.travis.yml +++ b/.travis.yml @@ -21,8 +21,8 @@ branches: - release-2.3 install: - - npm uninstall typescript - - npm uninstall tslint + - npm uninstall typescript --no-save + - npm uninstall tslint --no-save - npm install cache: diff --git a/jenkins.sh b/jenkins.sh index 377a44b7bf7..b716f5bbeb2 100755 --- a/jenkins.sh +++ b/jenkins.sh @@ -2,12 +2,12 @@ # Set up NVM export NVM_DIR="/home/dotnet-bot/.nvm" -[ -s "$NVM_DIR/nvm.sh" ] && . "$NVM_DIR/nvm.sh" +[ -s "$NVM_DIR/nvm.sh" ] && . "$NVM_DIR/nvm.sh" nvm install $1 -npm uninstall typescript -npm uninstall tslint +npm uninstall typescript --no-save +npm uninstall tslint --no-save npm install npm update npm test From 3eda9c627bfff7f6653ac3363c33a778862aa6d2 Mon Sep 17 00:00:00 2001 From: Andy Date: Wed, 31 May 2017 07:45:13 -0700 Subject: [PATCH 52/56] Make node type predicates public (#16121) * Make node type predicates public * Rename isJSDocComment back to isJSDoc --- src/compiler/checker.ts | 6 +- src/compiler/factory.ts | 4 +- src/compiler/transformers/es2015.ts | 4 +- src/compiler/transformers/module/system.ts | 2 +- src/compiler/utilities.ts | 2137 ++++++++++++-------- 5 files changed, 1327 insertions(+), 826 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 7ef6aa6217d..c5afb367cf4 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -21082,10 +21082,6 @@ namespace ts { } } - function isAccessor(kind: SyntaxKind): boolean { - return kind === SyntaxKind.GetAccessor || kind === SyntaxKind.SetAccessor; - } - function checkInheritedPropertiesAreIdentical(type: InterfaceType, typeNode: Node): boolean { const baseTypes = getBaseTypes(type); if (baseTypes.length < 2) { @@ -24555,7 +24551,7 @@ namespace ts { function checkGrammarStatementInAmbientContext(node: Node): boolean { if (isInAmbientContext(node)) { // An accessors is already reported about the ambient context - if (isAccessor(node.parent.kind)) { + if (isAccessor(node.parent)) { return getNodeLinks(node).hasReportedStatementInAmbientContext = true; } diff --git a/src/compiler/factory.ts b/src/compiler/factory.ts index 943d011c350..7c690e93155 100644 --- a/src/compiler/factory.ts +++ b/src/compiler/factory.ts @@ -3908,7 +3908,7 @@ namespace ts { return bindingElement.right; } - if (isSpreadExpression(bindingElement)) { + if (isSpreadElement(bindingElement)) { // Recovery consistent with existing emit. return getInitializerOfBindingOrAssignmentElement(bindingElement.expression); } @@ -3976,7 +3976,7 @@ namespace ts { return getTargetOfBindingOrAssignmentElement(bindingElement.left); } - if (isSpreadExpression(bindingElement)) { + if (isSpreadElement(bindingElement)) { // `a` in `[...a] = ...` return getTargetOfBindingOrAssignmentElement(bindingElement.expression); } diff --git a/src/compiler/transformers/es2015.ts b/src/compiler/transformers/es2015.ts index 63c10145165..b9ea70d4506 100644 --- a/src/compiler/transformers/es2015.ts +++ b/src/compiler/transformers/es2015.ts @@ -3396,7 +3396,7 @@ namespace ts { else { if (segments.length === 1) { const firstElement = elements[0]; - return needsUniqueCopy && isSpreadExpression(firstElement) && firstElement.expression.kind !== SyntaxKind.ArrayLiteralExpression + return needsUniqueCopy && isSpreadElement(firstElement) && firstElement.expression.kind !== SyntaxKind.ArrayLiteralExpression ? createArraySlice(segments[0]) : segments[0]; } @@ -3407,7 +3407,7 @@ namespace ts { } function partitionSpread(node: Expression) { - return isSpreadExpression(node) + return isSpreadElement(node) ? visitSpanOfSpreads : visitSpanOfNonSpreads; } diff --git a/src/compiler/transformers/module/system.ts b/src/compiler/transformers/module/system.ts index 3355ad35633..e6351c0965e 100644 --- a/src/compiler/transformers/module/system.ts +++ b/src/compiler/transformers/module/system.ts @@ -1502,7 +1502,7 @@ namespace ts { if (isAssignmentExpression(node, /*excludeCompoundAssignment*/ true)) { return hasExportedReferenceInDestructuringTarget(node.left); } - else if (isSpreadExpression(node)) { + else if (isSpreadElement(node)) { return hasExportedReferenceInDestructuringTarget(node.expression); } else if (isObjectLiteralExpression(node)) { diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 506d2728ffd..60e2fdf6679 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -254,10 +254,6 @@ namespace ts { return !nodeIsMissing(node); } - export function isToken(n: Node): boolean { - return n.kind >= SyntaxKind.FirstToken && n.kind <= SyntaxKind.LastToken; - } - export function getTokenPosOfNode(node: Node, sourceFile?: SourceFileLike, includeJsDoc?: boolean): number { // With nodes that have no width (i.e. 'Missing' nodes), we actually *don't* // want to skip trivia because this will launch us forward to the next token. @@ -284,22 +280,6 @@ namespace ts { return skipTrivia((sourceFile || getSourceFileOfNode(node)).text, node.pos); } - export function isJSDocNode(node: Node) { - return node.kind >= SyntaxKind.FirstJSDocNode && node.kind <= SyntaxKind.LastJSDocNode; - } - - export function isJSDoc(node: Node): node is JSDoc { - return node.kind === SyntaxKind.JSDocComment; - } - - export function isJSDocTypedefTag(node: Node): node is JSDocTypedefTag { - return node.kind === SyntaxKind.JSDocTypedefTag; - } - - export function isJSDocTag(node: Node) { - return node.kind >= SyntaxKind.FirstJSDocTagNode && node.kind <= SyntaxKind.LastJSDocTagNode; - } - export function getNonDecoratorTokenPosOfNode(node: Node, sourceFile?: SourceFileLike): number { if (nodeIsMissing(node) || !node.decorators) { return getTokenPosOfNode(node, sourceFile); @@ -743,10 +723,6 @@ namespace ts { return false; } - export function isPrefixUnaryExpression(node: Node): node is PrefixUnaryExpression { - return node.kind === SyntaxKind.PrefixUnaryExpression; - } - // Warning: This has the same semantics as the forEach family of functions, // in that traversal terminates in the event that 'visitor' supplies a truthy value. export function forEachReturnStatement(body: Block, visitor: (stmt: ReturnStatement) => T): T { @@ -854,49 +830,6 @@ namespace ts { return false; } - export function isAccessor(node: Node): node is AccessorDeclaration { - return node && (node.kind === SyntaxKind.GetAccessor || node.kind === SyntaxKind.SetAccessor); - } - - export function isClassLike(node: Node): node is ClassLikeDeclaration { - return node && (node.kind === SyntaxKind.ClassDeclaration || node.kind === SyntaxKind.ClassExpression); - } - - export function isFunctionLike(node: Node): node is FunctionLikeDeclaration { - return node && isFunctionLikeKind(node.kind); - } - - export function isFunctionLikeKind(kind: SyntaxKind): boolean { - switch (kind) { - case SyntaxKind.Constructor: - case SyntaxKind.FunctionExpression: - case SyntaxKind.FunctionDeclaration: - case SyntaxKind.ArrowFunction: - case SyntaxKind.MethodDeclaration: - case SyntaxKind.MethodSignature: - case SyntaxKind.GetAccessor: - case SyntaxKind.SetAccessor: - case SyntaxKind.CallSignature: - case SyntaxKind.ConstructSignature: - case SyntaxKind.IndexSignature: - case SyntaxKind.FunctionType: - case SyntaxKind.ConstructorType: - return true; - } - - return false; - } - - export function isFunctionOrConstructorTypeNode(node: Node): node is FunctionTypeNode | ConstructorTypeNode { - switch (node.kind) { - case SyntaxKind.FunctionType: - case SyntaxKind.ConstructorType: - return true; - } - - return false; - } - export function introducesArgumentsExoticObject(node: Node) { switch (node.kind) { case SyntaxKind.MethodDeclaration: @@ -911,21 +844,6 @@ namespace ts { return false; } - export function isIterationStatement(node: Node, lookInLabeledStatements: boolean): node is IterationStatement { - switch (node.kind) { - case SyntaxKind.ForStatement: - case SyntaxKind.ForInStatement: - case SyntaxKind.ForOfStatement: - case SyntaxKind.DoStatement: - case SyntaxKind.WhileStatement: - return true; - case SyntaxKind.LabeledStatement: - return lookInLabeledStatements && isIterationStatement((node).statement, lookInLabeledStatements); - } - - return false; - } - export function unwrapInnermostStatementOfLabel(node: LabeledStatement, beforeUnwrapLabelCallback?: (node: LabeledStatement) => void) { while (true) { if (beforeUnwrapLabelCallback) { @@ -1144,24 +1062,6 @@ namespace ts { return undefined; } - export function isCallLikeExpression(node: Node): node is CallLikeExpression { - switch (node.kind) { - case SyntaxKind.JsxOpeningElement: - case SyntaxKind.JsxSelfClosingElement: - case SyntaxKind.CallExpression: - case SyntaxKind.NewExpression: - case SyntaxKind.TaggedTemplateExpression: - case SyntaxKind.Decorator: - return true; - default: - return false; - } - } - - export function isCallOrNewExpression(node: Node): node is CallExpression | NewExpression { - return node.kind === SyntaxKind.CallExpression || node.kind === SyntaxKind.NewExpression; - } - export function getInvokedExpression(node: CallLikeExpression): Expression { if (node.kind === SyntaxKind.TaggedTemplateExpression) { return (node).tag; @@ -2012,10 +1912,6 @@ namespace ts { return false; } - export function isNumericLiteral(node: Node): node is NumericLiteral { - return node.kind === SyntaxKind.NumericLiteral; - } - export function isStringOrNumericLiteral(node: Node): node is StringLiteral | NumericLiteral { const kind = node.kind; return kind === SyntaxKind.StringLiteral @@ -2082,24 +1978,6 @@ namespace ts { return node.text === "push" || node.text === "unshift"; } - export function isModifierKind(token: SyntaxKind): boolean { - switch (token) { - case SyntaxKind.AbstractKeyword: - case SyntaxKind.AsyncKeyword: - case SyntaxKind.ConstKeyword: - case SyntaxKind.DeclareKeyword: - case SyntaxKind.DefaultKeyword: - case SyntaxKind.ExportKeyword: - case SyntaxKind.PublicKeyword: - case SyntaxKind.PrivateKeyword: - case SyntaxKind.ProtectedKeyword: - case SyntaxKind.ReadonlyKeyword: - case SyntaxKind.StaticKeyword: - return true; - } - return false; - } - export function isParameterDeclaration(node: VariableLikeDeclaration) { const root = getRootDeclaration(node); return root.kind === SyntaxKind.Parameter; @@ -3563,700 +3441,6 @@ namespace ts { return node.symbol && getDeclarationOfKind(node.symbol, kind) === node; } - // Node tests - // - // All node tests in the following list should *not* reference parent pointers so that - // they may be used with transformations. - - // Node Arrays - - export function isNodeArray(array: T[]): array is NodeArray { - return array.hasOwnProperty("pos") - && array.hasOwnProperty("end"); - } - - // Literals - - export function isNoSubstitutionTemplateLiteral(node: Node): node is LiteralExpression { - return node.kind === SyntaxKind.NoSubstitutionTemplateLiteral; - } - - export function isLiteralKind(kind: SyntaxKind): boolean { - return SyntaxKind.FirstLiteralToken <= kind && kind <= SyntaxKind.LastLiteralToken; - } - - export function isTextualLiteralKind(kind: SyntaxKind): boolean { - return kind === SyntaxKind.StringLiteral || kind === SyntaxKind.NoSubstitutionTemplateLiteral; - } - - export function isLiteralExpression(node: Node): node is LiteralExpression { - return isLiteralKind(node.kind); - } - - // Pseudo-literals - - export function isTemplateLiteralKind(kind: SyntaxKind): boolean { - return SyntaxKind.FirstTemplateToken <= kind && kind <= SyntaxKind.LastTemplateToken; - } - - export function isTemplateHead(node: Node): node is TemplateHead { - return node.kind === SyntaxKind.TemplateHead; - } - - export function isTemplateMiddleOrTemplateTail(node: Node): node is TemplateMiddle | TemplateTail { - const kind = node.kind; - return kind === SyntaxKind.TemplateMiddle - || kind === SyntaxKind.TemplateTail; - } - - // Identifiers - - export function isIdentifier(node: Node): node is Identifier { - return node.kind === SyntaxKind.Identifier; - } - - export function isGeneratedIdentifier(node: Node): node is GeneratedIdentifier { - // Using `>` here catches both `GeneratedIdentifierKind.None` and `undefined`. - return isIdentifier(node) && node.autoGenerateKind > GeneratedIdentifierKind.None; - } - - // Keywords - - export function isModifier(node: Node): node is Modifier { - return isModifierKind(node.kind); - } - - // Names - - export function isQualifiedName(node: Node): node is QualifiedName { - return node.kind === SyntaxKind.QualifiedName; - } - - export function isComputedPropertyName(node: Node): node is ComputedPropertyName { - return node.kind === SyntaxKind.ComputedPropertyName; - } - - export function isEntityName(node: Node): node is EntityName { - const kind = node.kind; - return kind === SyntaxKind.QualifiedName - || kind === SyntaxKind.Identifier; - } - - export function isPropertyName(node: Node): node is PropertyName { - const kind = node.kind; - return kind === SyntaxKind.Identifier - || kind === SyntaxKind.StringLiteral - || kind === SyntaxKind.NumericLiteral - || kind === SyntaxKind.ComputedPropertyName; - } - - export function isModuleName(node: Node): node is ModuleName { - const kind = node.kind; - return kind === SyntaxKind.Identifier - || kind === SyntaxKind.StringLiteral; - } - - export function isBindingName(node: Node): node is BindingName { - const kind = node.kind; - return kind === SyntaxKind.Identifier - || kind === SyntaxKind.ObjectBindingPattern - || kind === SyntaxKind.ArrayBindingPattern; - } - - // Signature elements - - export function isTypeParameter(node: Node): node is TypeParameterDeclaration { - return node.kind === SyntaxKind.TypeParameter; - } - - export function isParameter(node: Node): node is ParameterDeclaration { - return node.kind === SyntaxKind.Parameter; - } - - export function isDecorator(node: Node): node is Decorator { - return node.kind === SyntaxKind.Decorator; - } - - // Type members - - export function isMethodDeclaration(node: Node): node is MethodDeclaration { - return node.kind === SyntaxKind.MethodDeclaration; - } - - export function isClassElement(node: Node): node is ClassElement { - const kind = node.kind; - return kind === SyntaxKind.Constructor - || kind === SyntaxKind.PropertyDeclaration - || kind === SyntaxKind.MethodDeclaration - || kind === SyntaxKind.GetAccessor - || kind === SyntaxKind.SetAccessor - || kind === SyntaxKind.IndexSignature - || kind === SyntaxKind.SemicolonClassElement - || kind === SyntaxKind.MissingDeclaration; - } - - export function isTypeElement(node: Node): node is TypeElement { - const kind = node.kind; - return kind === SyntaxKind.ConstructSignature - || kind === SyntaxKind.CallSignature - || kind === SyntaxKind.PropertySignature - || kind === SyntaxKind.MethodSignature - || kind === SyntaxKind.IndexSignature - || kind === SyntaxKind.MissingDeclaration; - } - - export function isObjectLiteralElementLike(node: Node): node is ObjectLiteralElementLike { - const kind = node.kind; - return kind === SyntaxKind.PropertyAssignment - || kind === SyntaxKind.ShorthandPropertyAssignment - || kind === SyntaxKind.SpreadAssignment - || kind === SyntaxKind.MethodDeclaration - || kind === SyntaxKind.GetAccessor - || kind === SyntaxKind.SetAccessor - || kind === SyntaxKind.MissingDeclaration; - } - - // Type - - function isTypeNodeKind(kind: SyntaxKind) { - return (kind >= SyntaxKind.FirstTypeNode && kind <= SyntaxKind.LastTypeNode) - || kind === SyntaxKind.AnyKeyword - || kind === SyntaxKind.NumberKeyword - || kind === SyntaxKind.ObjectKeyword - || kind === SyntaxKind.BooleanKeyword - || kind === SyntaxKind.StringKeyword - || kind === SyntaxKind.SymbolKeyword - || kind === SyntaxKind.ThisKeyword - || kind === SyntaxKind.VoidKeyword - || kind === SyntaxKind.UndefinedKeyword - || kind === SyntaxKind.NullKeyword - || kind === SyntaxKind.NeverKeyword - || kind === SyntaxKind.ExpressionWithTypeArguments; - } - - /** - * Node test that determines whether a node is a valid type node. - * This differs from the `isPartOfTypeNode` function which determines whether a node is *part* - * of a TypeNode. - */ - export function isTypeNode(node: Node): node is TypeNode { - return isTypeNodeKind(node.kind); - } - - // Binding patterns - - export function isArrayBindingPattern(node: Node): node is ArrayBindingPattern { - return node.kind === SyntaxKind.ArrayBindingPattern; - } - - export function isObjectBindingPattern(node: Node): node is ObjectBindingPattern { - return node.kind === SyntaxKind.ObjectBindingPattern; - } - - export function isBindingPattern(node: Node): node is BindingPattern { - if (node) { - const kind = node.kind; - return kind === SyntaxKind.ArrayBindingPattern - || kind === SyntaxKind.ObjectBindingPattern; - } - - return false; - } - - export function isAssignmentPattern(node: Node): node is AssignmentPattern { - const kind = node.kind; - return kind === SyntaxKind.ArrayLiteralExpression - || kind === SyntaxKind.ObjectLiteralExpression; - } - - export function isBindingElement(node: Node): node is BindingElement { - return node.kind === SyntaxKind.BindingElement; - } - - export function isArrayBindingElement(node: Node): node is ArrayBindingElement { - const kind = node.kind; - return kind === SyntaxKind.BindingElement - || kind === SyntaxKind.OmittedExpression; - } - - - /** - * Determines whether the BindingOrAssignmentElement is a BindingElement-like declaration - */ - export function isDeclarationBindingElement(bindingElement: BindingOrAssignmentElement): bindingElement is VariableDeclaration | ParameterDeclaration | BindingElement { - switch (bindingElement.kind) { - case SyntaxKind.VariableDeclaration: - case SyntaxKind.Parameter: - case SyntaxKind.BindingElement: - return true; - } - - return false; - } - - /** - * Determines whether a node is a BindingOrAssignmentPattern - */ - export function isBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is BindingOrAssignmentPattern { - return isObjectBindingOrAssignmentPattern(node) - || isArrayBindingOrAssignmentPattern(node); - } - - /** - * Determines whether a node is an ObjectBindingOrAssignmentPattern - */ - export function isObjectBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is ObjectBindingOrAssignmentPattern { - switch (node.kind) { - case SyntaxKind.ObjectBindingPattern: - case SyntaxKind.ObjectLiteralExpression: - return true; - } - - return false; - } - - /** - * Determines whether a node is an ArrayBindingOrAssignmentPattern - */ - export function isArrayBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is ArrayBindingOrAssignmentPattern { - switch (node.kind) { - case SyntaxKind.ArrayBindingPattern: - case SyntaxKind.ArrayLiteralExpression: - return true; - } - - return false; - } - - // Expression - - export function isArrayLiteralExpression(node: Node): node is ArrayLiteralExpression { - return node.kind === SyntaxKind.ArrayLiteralExpression; - } - - export function isObjectLiteralExpression(node: Node): node is ObjectLiteralExpression { - return node.kind === SyntaxKind.ObjectLiteralExpression; - } - - export function isPropertyAccessExpression(node: Node): node is PropertyAccessExpression { - return node.kind === SyntaxKind.PropertyAccessExpression; - } - - export function isPropertyAccessOrQualifiedName(node: Node): node is PropertyAccessExpression | QualifiedName { - const kind = node.kind; - return kind === SyntaxKind.PropertyAccessExpression - || kind === SyntaxKind.QualifiedName; - } - - export function isElementAccessExpression(node: Node): node is ElementAccessExpression { - return node.kind === SyntaxKind.ElementAccessExpression; - } - - export function isBinaryExpression(node: Node): node is BinaryExpression { - return node.kind === SyntaxKind.BinaryExpression; - } - - export function isConditionalExpression(node: Node): node is ConditionalExpression { - return node.kind === SyntaxKind.ConditionalExpression; - } - - export function isCallExpression(node: Node): node is CallExpression { - return node.kind === SyntaxKind.CallExpression; - } - - export function isTemplateLiteral(node: Node): node is TemplateLiteral { - const kind = node.kind; - return kind === SyntaxKind.TemplateExpression - || kind === SyntaxKind.NoSubstitutionTemplateLiteral; - } - - export function isSpreadExpression(node: Node): node is SpreadElement { - return node.kind === SyntaxKind.SpreadElement; - } - - export function isExpressionWithTypeArguments(node: Node): node is ExpressionWithTypeArguments { - return node.kind === SyntaxKind.ExpressionWithTypeArguments; - } - - function isLeftHandSideExpressionKind(kind: SyntaxKind): boolean { - return kind === SyntaxKind.PropertyAccessExpression - || kind === SyntaxKind.ElementAccessExpression - || kind === SyntaxKind.NewExpression - || kind === SyntaxKind.CallExpression - || kind === SyntaxKind.JsxElement - || kind === SyntaxKind.JsxSelfClosingElement - || kind === SyntaxKind.TaggedTemplateExpression - || kind === SyntaxKind.ArrayLiteralExpression - || kind === SyntaxKind.ParenthesizedExpression - || kind === SyntaxKind.ObjectLiteralExpression - || kind === SyntaxKind.ClassExpression - || kind === SyntaxKind.FunctionExpression - || kind === SyntaxKind.Identifier - || kind === SyntaxKind.RegularExpressionLiteral - || kind === SyntaxKind.NumericLiteral - || kind === SyntaxKind.StringLiteral - || kind === SyntaxKind.NoSubstitutionTemplateLiteral - || kind === SyntaxKind.TemplateExpression - || kind === SyntaxKind.FalseKeyword - || kind === SyntaxKind.NullKeyword - || kind === SyntaxKind.ThisKeyword - || kind === SyntaxKind.TrueKeyword - || kind === SyntaxKind.SuperKeyword - || kind === SyntaxKind.NonNullExpression - || kind === SyntaxKind.MetaProperty; - } - - export function isLeftHandSideExpression(node: Node): node is LeftHandSideExpression { - return isLeftHandSideExpressionKind(skipPartiallyEmittedExpressions(node).kind); - } - - function isUnaryExpressionKind(kind: SyntaxKind): boolean { - return kind === SyntaxKind.PrefixUnaryExpression - || kind === SyntaxKind.PostfixUnaryExpression - || kind === SyntaxKind.DeleteExpression - || kind === SyntaxKind.TypeOfExpression - || kind === SyntaxKind.VoidExpression - || kind === SyntaxKind.AwaitExpression - || kind === SyntaxKind.TypeAssertionExpression - || isLeftHandSideExpressionKind(kind); - } - - export function isUnaryExpression(node: Node): node is UnaryExpression { - return isUnaryExpressionKind(skipPartiallyEmittedExpressions(node).kind); - } - - function isExpressionKind(kind: SyntaxKind) { - return kind === SyntaxKind.ConditionalExpression - || kind === SyntaxKind.YieldExpression - || kind === SyntaxKind.ArrowFunction - || kind === SyntaxKind.BinaryExpression - || kind === SyntaxKind.SpreadElement - || kind === SyntaxKind.AsExpression - || kind === SyntaxKind.OmittedExpression - || kind === SyntaxKind.CommaListExpression - || isUnaryExpressionKind(kind); - } - - export function isExpression(node: Node): node is Expression { - return isExpressionKind(skipPartiallyEmittedExpressions(node).kind); - } - - export function isAssertionExpression(node: Node): node is AssertionExpression { - const kind = node.kind; - return kind === SyntaxKind.TypeAssertionExpression - || kind === SyntaxKind.AsExpression; - } - - export function isPartiallyEmittedExpression(node: Node): node is PartiallyEmittedExpression { - return node.kind === SyntaxKind.PartiallyEmittedExpression; - } - - export function isNotEmittedStatement(node: Node): node is NotEmittedStatement { - return node.kind === SyntaxKind.NotEmittedStatement; - } - - export function isNotEmittedOrPartiallyEmittedNode(node: Node): node is NotEmittedStatement | PartiallyEmittedExpression { - return isNotEmittedStatement(node) - || isPartiallyEmittedExpression(node); - } - - export function isOmittedExpression(node: Node): node is OmittedExpression { - return node.kind === SyntaxKind.OmittedExpression; - } - - // Misc - - export function isTemplateSpan(node: Node): node is TemplateSpan { - return node.kind === SyntaxKind.TemplateSpan; - } - - // Element - - export function isBlock(node: Node): node is Block { - return node.kind === SyntaxKind.Block; - } - - export function isConciseBody(node: Node): node is ConciseBody { - return isBlock(node) - || isExpression(node); - } - - export function isFunctionBody(node: Node): node is FunctionBody { - return isBlock(node); - } - - export function isForInitializer(node: Node): node is ForInitializer { - return isVariableDeclarationList(node) - || isExpression(node); - } - - export function isVariableDeclaration(node: Node): node is VariableDeclaration { - return node.kind === SyntaxKind.VariableDeclaration; - } - - export function isVariableDeclarationList(node: Node): node is VariableDeclarationList { - return node.kind === SyntaxKind.VariableDeclarationList; - } - - export function isCaseBlock(node: Node): node is CaseBlock { - return node.kind === SyntaxKind.CaseBlock; - } - - export function isModuleBody(node: Node): node is ModuleBody { - const kind = node.kind; - return kind === SyntaxKind.ModuleBlock - || kind === SyntaxKind.ModuleDeclaration - || kind === SyntaxKind.Identifier; - } - - export function isNamespaceBody(node: Node): node is NamespaceBody { - const kind = node.kind; - return kind === SyntaxKind.ModuleBlock - || kind === SyntaxKind.ModuleDeclaration; - } - - export function isJSDocNamespaceBody(node: Node): node is JSDocNamespaceBody { - const kind = node.kind; - return kind === SyntaxKind.Identifier - || kind === SyntaxKind.ModuleDeclaration; - } - - export function isImportEqualsDeclaration(node: Node): node is ImportEqualsDeclaration { - return node.kind === SyntaxKind.ImportEqualsDeclaration; - } - - export function isImportDeclaration(node: Node): node is ImportDeclaration { - return node.kind === SyntaxKind.ImportDeclaration; - } - - export function isImportClause(node: Node): node is ImportClause { - return node.kind === SyntaxKind.ImportClause; - } - - export function isNamedImportBindings(node: Node): node is NamedImportBindings { - const kind = node.kind; - return kind === SyntaxKind.NamedImports - || kind === SyntaxKind.NamespaceImport; - } - - export function isImportSpecifier(node: Node): node is ImportSpecifier { - return node.kind === SyntaxKind.ImportSpecifier; - } - - export function isNamedExports(node: Node): node is NamedExports { - return node.kind === SyntaxKind.NamedExports; - } - - export function isExportSpecifier(node: Node): node is ExportSpecifier { - return node.kind === SyntaxKind.ExportSpecifier; - } - - export function isExportAssignment(node: Node): node is ExportAssignment { - return node.kind === SyntaxKind.ExportAssignment; - } - - export function isModuleOrEnumDeclaration(node: Node): node is ModuleDeclaration | EnumDeclaration { - return node.kind === SyntaxKind.ModuleDeclaration || node.kind === SyntaxKind.EnumDeclaration; - } - - function isDeclarationKind(kind: SyntaxKind) { - return kind === SyntaxKind.ArrowFunction - || kind === SyntaxKind.BindingElement - || kind === SyntaxKind.ClassDeclaration - || kind === SyntaxKind.ClassExpression - || kind === SyntaxKind.Constructor - || kind === SyntaxKind.EnumDeclaration - || kind === SyntaxKind.EnumMember - || kind === SyntaxKind.ExportSpecifier - || kind === SyntaxKind.FunctionDeclaration - || kind === SyntaxKind.FunctionExpression - || kind === SyntaxKind.GetAccessor - || kind === SyntaxKind.ImportClause - || kind === SyntaxKind.ImportEqualsDeclaration - || kind === SyntaxKind.ImportSpecifier - || kind === SyntaxKind.InterfaceDeclaration - || kind === SyntaxKind.JsxAttribute - || kind === SyntaxKind.MethodDeclaration - || kind === SyntaxKind.MethodSignature - || kind === SyntaxKind.ModuleDeclaration - || kind === SyntaxKind.NamespaceExportDeclaration - || kind === SyntaxKind.NamespaceImport - || kind === SyntaxKind.Parameter - || kind === SyntaxKind.PropertyAssignment - || kind === SyntaxKind.PropertyDeclaration - || kind === SyntaxKind.PropertySignature - || kind === SyntaxKind.SetAccessor - || kind === SyntaxKind.ShorthandPropertyAssignment - || kind === SyntaxKind.TypeAliasDeclaration - || kind === SyntaxKind.TypeParameter - || kind === SyntaxKind.VariableDeclaration - || kind === SyntaxKind.JSDocTypedefTag; - } - - function isDeclarationStatementKind(kind: SyntaxKind) { - return kind === SyntaxKind.FunctionDeclaration - || kind === SyntaxKind.MissingDeclaration - || kind === SyntaxKind.ClassDeclaration - || kind === SyntaxKind.InterfaceDeclaration - || kind === SyntaxKind.TypeAliasDeclaration - || kind === SyntaxKind.EnumDeclaration - || kind === SyntaxKind.ModuleDeclaration - || kind === SyntaxKind.ImportDeclaration - || kind === SyntaxKind.ImportEqualsDeclaration - || kind === SyntaxKind.ExportDeclaration - || kind === SyntaxKind.ExportAssignment - || kind === SyntaxKind.NamespaceExportDeclaration; - } - - function isStatementKindButNotDeclarationKind(kind: SyntaxKind) { - return kind === SyntaxKind.BreakStatement - || kind === SyntaxKind.ContinueStatement - || kind === SyntaxKind.DebuggerStatement - || kind === SyntaxKind.DoStatement - || kind === SyntaxKind.ExpressionStatement - || kind === SyntaxKind.EmptyStatement - || kind === SyntaxKind.ForInStatement - || kind === SyntaxKind.ForOfStatement - || kind === SyntaxKind.ForStatement - || kind === SyntaxKind.IfStatement - || kind === SyntaxKind.LabeledStatement - || kind === SyntaxKind.ReturnStatement - || kind === SyntaxKind.SwitchStatement - || kind === SyntaxKind.ThrowStatement - || kind === SyntaxKind.TryStatement - || kind === SyntaxKind.VariableStatement - || kind === SyntaxKind.WhileStatement - || kind === SyntaxKind.WithStatement - || kind === SyntaxKind.NotEmittedStatement - || kind === SyntaxKind.EndOfDeclarationMarker - || kind === SyntaxKind.MergeDeclarationMarker; - } - - export function isDeclaration(node: Node): node is NamedDeclaration { - return isDeclarationKind(node.kind); - } - - export function isDeclarationStatement(node: Node): node is DeclarationStatement { - return isDeclarationStatementKind(node.kind); - } - - /** - * Determines whether the node is a statement that is not also a declaration - */ - export function isStatementButNotDeclaration(node: Node): node is Statement { - return isStatementKindButNotDeclarationKind(node.kind); - } - - export function isStatement(node: Node): node is Statement { - const kind = node.kind; - return isStatementKindButNotDeclarationKind(kind) - || isDeclarationStatementKind(kind) - || kind === SyntaxKind.Block; - } - - // Module references - - export function isModuleReference(node: Node): node is ModuleReference { - const kind = node.kind; - return kind === SyntaxKind.ExternalModuleReference - || kind === SyntaxKind.QualifiedName - || kind === SyntaxKind.Identifier; - } - - // JSX - - export function isJsxOpeningElement(node: Node): node is JsxOpeningElement { - return node.kind === SyntaxKind.JsxOpeningElement; - } - - export function isJsxClosingElement(node: Node): node is JsxClosingElement { - return node.kind === SyntaxKind.JsxClosingElement; - } - - export function isJsxTagNameExpression(node: Node): node is JsxTagNameExpression { - const kind = node.kind; - return kind === SyntaxKind.ThisKeyword - || kind === SyntaxKind.Identifier - || kind === SyntaxKind.PropertyAccessExpression; - } - - export function isJsxChild(node: Node): node is JsxChild { - const kind = node.kind; - return kind === SyntaxKind.JsxElement - || kind === SyntaxKind.JsxExpression - || kind === SyntaxKind.JsxSelfClosingElement - || kind === SyntaxKind.JsxText; - } - - export function isJsxAttributes(node: Node): node is JsxAttributes { - const kind = node.kind; - return kind === SyntaxKind.JsxAttributes; - } - - export function isJsxAttributeLike(node: Node): node is JsxAttributeLike { - const kind = node.kind; - return kind === SyntaxKind.JsxAttribute - || kind === SyntaxKind.JsxSpreadAttribute; - } - - export function isJsxSpreadAttribute(node: Node): node is JsxSpreadAttribute { - return node.kind === SyntaxKind.JsxSpreadAttribute; - } - - export function isJsxAttribute(node: Node): node is JsxAttribute { - return node.kind === SyntaxKind.JsxAttribute; - } - - export function isStringLiteralOrJsxExpression(node: Node): node is StringLiteral | JsxExpression { - const kind = node.kind; - return kind === SyntaxKind.StringLiteral - || kind === SyntaxKind.JsxExpression; - } - - export function isJsxOpeningLikeElement(node: Node): node is JsxOpeningLikeElement { - const kind = node.kind; - return kind === SyntaxKind.JsxOpeningElement - || kind === SyntaxKind.JsxSelfClosingElement; - } - - // Clauses - - export function isCaseOrDefaultClause(node: Node): node is CaseOrDefaultClause { - const kind = node.kind; - return kind === SyntaxKind.CaseClause - || kind === SyntaxKind.DefaultClause; - } - - export function isHeritageClause(node: Node): node is HeritageClause { - return node.kind === SyntaxKind.HeritageClause; - } - - export function isCatchClause(node: Node): node is CatchClause { - return node.kind === SyntaxKind.CatchClause; - } - - - // Property assignments - - export function isPropertyAssignment(node: Node): node is PropertyAssignment { - return node.kind === SyntaxKind.PropertyAssignment; - } - - export function isShorthandPropertyAssignment(node: Node): node is ShorthandPropertyAssignment { - return node.kind === SyntaxKind.ShorthandPropertyAssignment; - } - - // Enum - - export function isEnumMember(node: Node): node is EnumMember { - return node.kind === SyntaxKind.EnumMember; - } - - // Top-level nodes - export function isSourceFile(node: Node): node is SourceFile { - return node.kind === SyntaxKind.SourceFile; - } - export function isWatchSet(options: CompilerOptions) { // Firefox has Object.prototype.watch return options.watch && options.hasOwnProperty("watch"); @@ -4759,3 +3943,1324 @@ namespace ts { } } } + +// Simple node tests of the form `node.kind === SyntaxKind.Foo`. +namespace ts { + // Literals + export function isNumericLiteral(node: Node): node is NumericLiteral { + return node.kind === SyntaxKind.NumericLiteral; + } + + export function isStringLiteral(node: Node): node is StringLiteral { + return node.kind === SyntaxKind.StringLiteral; + } + + export function isJsxText(node: Node): node is JsxText { + return node.kind === SyntaxKind.JsxText; + } + + export function isRegularExpressionLiteral(node: Node): node is RegularExpressionLiteral { + return node.kind === SyntaxKind.RegularExpressionLiteral; + } + + export function isNoSubstitutionTemplateLiteral(node: Node): node is LiteralExpression { + return node.kind === SyntaxKind.NoSubstitutionTemplateLiteral; + } + + // Pseudo-literals + + export function isTemplateHead(node: Node): node is TemplateHead { + return node.kind === SyntaxKind.TemplateHead; + } + + export function isTemplateMiddle(node: Node): node is TemplateMiddle { + return node.kind === SyntaxKind.TemplateMiddle; + } + + export function isTemplateTail(node: Node): node is TemplateTail { + return node.kind === SyntaxKind.TemplateTail; + } + + export function isIdentifier(node: Node): node is Identifier { + return node.kind === SyntaxKind.Identifier; + } + + // Names + + export function isQualifiedName(node: Node): node is QualifiedName { + return node.kind === SyntaxKind.QualifiedName; + } + + export function isComputedPropertyName(node: Node): node is ComputedPropertyName { + return node.kind === SyntaxKind.ComputedPropertyName; + } + + // Signature elements + + export function isTypeParameter(node: Node): node is TypeParameterDeclaration { + return node.kind === SyntaxKind.TypeParameter; + } + + export function isParameter(node: Node): node is ParameterDeclaration { + return node.kind === SyntaxKind.Parameter; + } + + export function isDecorator(node: Node): node is Decorator { + return node.kind === SyntaxKind.Decorator; + } + + // TypeMember + + export function isPropertySignature(node: Node): node is PropertySignature { + return node.kind === SyntaxKind.PropertySignature; + } + + export function isPropertyDeclaration(node: Node): node is PropertyDeclaration { + return node.kind === SyntaxKind.PropertyDeclaration; + } + + export function isMethodSignature(node: Node): node is MethodSignature { + return node.kind === SyntaxKind.MethodSignature; + } + + export function isMethodDeclaration(node: Node): node is MethodDeclaration { + return node.kind === SyntaxKind.MethodDeclaration; + } + + export function isConstructorDeclaration(node: Node): node is ConstructorDeclaration { + return node.kind === SyntaxKind.Constructor; + } + + export function isGetAccessorDeclaration(node: Node): node is GetAccessorDeclaration { + return node.kind === SyntaxKind.GetAccessor; + } + + export function isSetAccessorDeclaration(node: Node): node is SetAccessorDeclaration { + return node.kind === SyntaxKind.SetAccessor; + } + + export function isCallSignatureDeclaration(node: Node): node is CallSignatureDeclaration { + return node.kind === SyntaxKind.CallSignature; + } + + export function isConstructSignatureDeclaration(node: Node): node is ConstructSignatureDeclaration { + return node.kind === SyntaxKind.ConstructSignature; + } + + export function isIndexSignatureDeclaration(node: Node): node is IndexSignatureDeclaration { + return node.kind === SyntaxKind.IndexSignature; + } + + // Type + + export function isTypePredicateNode(node: Node): node is TypePredicateNode { + return node.kind === SyntaxKind.TypePredicate; + } + + export function isTypeReferenceNode(node: Node): node is TypeReferenceNode { + return node.kind === SyntaxKind.TypeReference; + } + + export function isFunctionTypeNode(node: Node): node is FunctionTypeNode { + return node.kind === SyntaxKind.FunctionType; + } + + export function isConstructorTypeNode(node: Node): node is ConstructorTypeNode { + return node.kind === SyntaxKind.ConstructorType; + } + + export function isTypeQueryNode(node: Node): node is TypeQueryNode { + return node.kind === SyntaxKind.TypeQuery; + } + + export function isTypeLiteralNode(node: Node): node is TypeLiteralNode { + return node.kind === SyntaxKind.TypeLiteral; + } + + export function isArrayTypeNode(node: Node): node is ArrayTypeNode { + return node.kind === SyntaxKind.ArrayType; + } + + export function isTupleTypeNode(node: Node): node is TupleTypeNode { + return node.kind === SyntaxKind.TupleType; + } + + export function isUnionTypeNode(node: Node): node is UnionTypeNode { + return node.kind === SyntaxKind.UnionType; + } + + export function isIntersectionTypeNode(node: Node): node is IntersectionTypeNode { + return node.kind === SyntaxKind.IntersectionType; + } + + export function isParenthesizedTypeNode(node: Node): node is ParenthesizedTypeNode { + return node.kind === SyntaxKind.ParenthesizedType; + } + + export function isThisTypeNode(node: Node): node is ThisTypeNode { + return node.kind === SyntaxKind.ThisType; + } + + export function isTypeOperatorNode(node: Node): node is TypeOperatorNode { + return node.kind === SyntaxKind.TypeOperator; + } + + export function isIndexedAccessTypeNode(node: Node): node is IndexedAccessTypeNode { + return node.kind === SyntaxKind.IndexedAccessType; + } + + export function isMappedTypeNode(node: Node): node is MappedTypeNode { + return node.kind === SyntaxKind.MappedType; + } + + export function isLiteralTypeNode(node: Node): node is LiteralTypeNode { + return node.kind === SyntaxKind.LiteralType; + } + + // Binding patterns + + export function isObjectBindingPattern(node: Node): node is ObjectBindingPattern { + return node.kind === SyntaxKind.ObjectBindingPattern; + } + + export function isArrayBindingPattern(node: Node): node is ArrayBindingPattern { + return node.kind === SyntaxKind.ArrayBindingPattern; + } + + export function isBindingElement(node: Node): node is BindingElement { + return node.kind === SyntaxKind.BindingElement; + } + + // Expression + + export function isArrayLiteralExpression(node: Node): node is ArrayLiteralExpression { + return node.kind === SyntaxKind.ArrayLiteralExpression; + } + + export function isObjectLiteralExpression(node: Node): node is ObjectLiteralExpression { + return node.kind === SyntaxKind.ObjectLiteralExpression; + } + + export function isPropertyAccessExpression(node: Node): node is PropertyAccessExpression { + return node.kind === SyntaxKind.PropertyAccessExpression; + } + + export function isElementAccessExpression(node: Node): node is ElementAccessExpression { + return node.kind === SyntaxKind.ElementAccessExpression; + } + + export function isCallExpression(node: Node): node is CallExpression { + return node.kind === SyntaxKind.CallExpression; + } + + export function isNewExpression(node: Node): node is NewExpression { + return node.kind === SyntaxKind.NewExpression; + } + + export function isTaggedTemplateExpression(node: Node): node is TaggedTemplateExpression { + return node.kind === SyntaxKind.TaggedTemplateExpression; + } + + export function isTypeAssertion(node: Node): node is TypeAssertion { + return node.kind === SyntaxKind.TypeAssertionExpression; + } + + export function isParenthesizedExpression(node: Node): node is ParenthesizedExpression { + return node.kind === SyntaxKind.ParenthesizedExpression; + } + + export function isFunctionExpression(node: Node): node is FunctionExpression { + return node.kind === SyntaxKind.FunctionExpression; + } + + export function isArrowFunction(node: Node): node is ArrowFunction { + return node.kind === SyntaxKind.ArrowFunction; + } + + export function isDeleteExpression(node: Node): node is DeleteExpression { + return node.kind === SyntaxKind.DeleteExpression; + } + + export function isTypeOfExpression(node: Node): node is TypeOfExpression { + return node.kind === SyntaxKind.AwaitExpression; + } + + export function isVoidExpression(node: Node): node is VoidExpression { + return node.kind === SyntaxKind.VoidExpression; + } + + export function isAwaitExpression(node: Node): node is AwaitExpression { + return node.kind === SyntaxKind.AwaitExpression; + } + + export function isPrefixUnaryExpression(node: Node): node is PrefixUnaryExpression { + return node.kind === SyntaxKind.PrefixUnaryExpression; + } + + export function isPostfixUnaryExpression(node: Node): node is PostfixUnaryExpression { + return node.kind === SyntaxKind.PostfixUnaryExpression; + } + + export function isBinaryExpression(node: Node): node is BinaryExpression { + return node.kind === SyntaxKind.BinaryExpression; + } + + export function isConditionalExpression(node: Node): node is ConditionalExpression { + return node.kind === SyntaxKind.ConditionalExpression; + } + + export function isTemplateExpression(node: Node): node is TemplateExpression { + return node.kind === SyntaxKind.TemplateExpression; + } + + export function isYieldExpression(node: Node): node is YieldExpression { + return node.kind === SyntaxKind.YieldExpression; + } + + export function isSpreadElement(node: Node): node is SpreadElement { + return node.kind === SyntaxKind.SpreadElement; + } + + export function isClassExpression(node: Node): node is ClassExpression { + return node.kind === SyntaxKind.ClassExpression; + } + + export function isOmittedExpression(node: Node): node is OmittedExpression { + return node.kind === SyntaxKind.OmittedExpression; + } + + export function isExpressionWithTypeArguments(node: Node): node is ExpressionWithTypeArguments { + return node.kind === SyntaxKind.ExpressionWithTypeArguments; + } + + export function isAsExpression(node: Node): node is AsExpression { + return node.kind === SyntaxKind.AsExpression; + } + + export function isNonNullExpression(node: Node): node is NonNullExpression { + return node.kind === SyntaxKind.NonNullExpression; + } + + export function isMetaProperty(node: Node): node is MetaProperty { + return node.kind === SyntaxKind.MetaProperty; + } + + // Misc + + export function isTemplateSpan(node: Node): node is TemplateSpan { + return node.kind === SyntaxKind.TemplateSpan; + } + + export function isSemicolonClassElement(node: Node): node is SemicolonClassElement { + return node.kind === SyntaxKind.SemicolonClassElement; + } + + // Block + + export function isBlock(node: Node): node is Block { + return node.kind === SyntaxKind.Block; + } + + export function isVariableStatement(node: Node): node is VariableStatement { + return node.kind === SyntaxKind.VariableStatement; + } + + export function isEmptyStatement(node: Node): node is EmptyStatement { + return node.kind === SyntaxKind.EmptyStatement; + } + + export function isExpressionStatement(node: Node): node is ExpressionStatement { + return node.kind === SyntaxKind.ExpressionStatement; + } + + export function isIfStatement(node: Node): node is IfStatement { + return node.kind === SyntaxKind.IfStatement; + } + + export function isDoStatement(node: Node): node is DoStatement { + return node.kind === SyntaxKind.DoStatement; + } + + export function isWhileStatement(node: Node): node is WhileStatement { + return node.kind === SyntaxKind.WhileStatement; + } + + export function isForStatement(node: Node): node is ForStatement { + return node.kind === SyntaxKind.ForStatement; + } + + export function isForInStatement(node: Node): node is ForInStatement { + return node.kind === SyntaxKind.ForInStatement; + } + + export function isForOfStatement(node: Node): node is ForOfStatement { + return node.kind === SyntaxKind.ForOfStatement; + } + + export function isContinueStatement(node: Node): node is ContinueStatement { + return node.kind === SyntaxKind.ContinueStatement; + } + + export function isBreakStatement(node: Node): node is BreakStatement { + return node.kind === SyntaxKind.BreakStatement; + } + + export function isReturnStatement(node: Node): node is ReturnStatement { + return node.kind === SyntaxKind.ReturnStatement; + } + + export function isWithStatement(node: Node): node is WithStatement { + return node.kind === SyntaxKind.WithStatement; + } + + export function isSwitchStatement(node: Node): node is SwitchStatement { + return node.kind === SyntaxKind.SwitchStatement; + } + + export function isLabeledStatement(node: Node): node is LabeledStatement { + return node.kind === SyntaxKind.LabeledStatement; + } + + export function isThrowStatement(node: Node): node is ThrowStatement { + return node.kind === SyntaxKind.ThrowStatement; + } + + export function isTryStatement(node: Node): node is TryStatement { + return node.kind === SyntaxKind.TryStatement; + } + + export function isDebuggerStatement(node: Node): node is DebuggerStatement { + return node.kind === SyntaxKind.DebuggerStatement; + } + + export function isVariableDeclaration(node: Node): node is VariableDeclaration { + return node.kind === SyntaxKind.VariableDeclaration; + } + + export function isVariableDeclarationList(node: Node): node is VariableDeclarationList { + return node.kind === SyntaxKind.VariableDeclarationList; + } + + export function isFunctionDeclaration(node: Node): node is FunctionDeclaration { + return node.kind === SyntaxKind.FunctionDeclaration; + } + + export function isClassDeclaration(node: Node): node is ClassDeclaration { + return node.kind === SyntaxKind.ClassDeclaration; + } + + export function isInterfaceDeclaration(node: Node): node is InterfaceDeclaration { + return node.kind === SyntaxKind.InterfaceDeclaration; + } + + export function isTypeAliasDeclaration(node: Node): node is TypeAliasDeclaration { + return node.kind === SyntaxKind.TypeAliasDeclaration; + } + + export function isEnumDeclaration(node: Node): node is EnumDeclaration { + return node.kind === SyntaxKind.EnumDeclaration; + } + + export function isModuleDeclaration(node: Node): node is ModuleDeclaration { + return node.kind === SyntaxKind.ModuleDeclaration; + } + + export function isModuleBlock(node: Node): node is ModuleBlock { + return node.kind === SyntaxKind.ModuleBlock; + } + + export function isCaseBlock(node: Node): node is CaseBlock { + return node.kind === SyntaxKind.CaseBlock; + } + + export function isNamespaceExportDeclaration(node: Node): node is NamespaceExportDeclaration { + return node.kind === SyntaxKind.NamespaceExportDeclaration; + } + + export function isImportEqualsDeclaration(node: Node): node is ImportEqualsDeclaration { + return node.kind === SyntaxKind.ImportEqualsDeclaration; + } + + export function isImportDeclaration(node: Node): node is ImportDeclaration { + return node.kind === SyntaxKind.ImportDeclaration; + } + + export function isImportClause(node: Node): node is ImportClause { + return node.kind === SyntaxKind.ImportClause; + } + + export function isNamespaceImport(node: Node): node is NamespaceImport { + return node.kind === SyntaxKind.NamespaceImport; + } + + export function isNamedImports(node: Node): node is NamedImports { + return node.kind === SyntaxKind.NamedImports; + } + + export function isImportSpecifier(node: Node): node is ImportSpecifier { + return node.kind === SyntaxKind.ImportSpecifier; + } + + export function isExportAssignment(node: Node): node is ExportAssignment { + return node.kind === SyntaxKind.ExportAssignment; + } + + export function isExportDeclaration(node: Node): node is ExportDeclaration { + return node.kind === SyntaxKind.ExportDeclaration; + } + + export function isNamedExports(node: Node): node is NamedExports { + return node.kind === SyntaxKind.NamedExports; + } + + export function isExportSpecifier(node: Node): node is ExportSpecifier { + return node.kind === SyntaxKind.ExportSpecifier; + } + + export function isMissingDeclaration(node: Node): node is MissingDeclaration { + return node.kind === SyntaxKind.MissingDeclaration; + } + + // Module References + + export function isExternalModuleReference(node: Node): node is ExternalModuleReference { + return node.kind === SyntaxKind.ExternalModuleReference; + } + + // JSX + + export function isJsxElement(node: Node): node is JsxElement { + return node.kind === SyntaxKind.JsxElement; + } + + export function isJsxSelfClosingElement(node: Node): node is JsxSelfClosingElement { + return node.kind === SyntaxKind.JsxSelfClosingElement; + } + + export function isJsxOpeningElement(node: Node): node is JsxOpeningElement { + return node.kind === SyntaxKind.JsxOpeningElement; + } + + export function isJsxClosingElement(node: Node): node is JsxClosingElement { + return node.kind === SyntaxKind.JsxClosingElement; + } + + export function isJsxAttribute(node: Node): node is JsxAttribute { + return node.kind === SyntaxKind.JsxAttribute; + } + + export function isJsxAttributes(node: Node): node is JsxAttributes { + return node.kind === SyntaxKind.JsxAttributes; + } + + export function isJsxSpreadAttribute(node: Node): node is JsxSpreadAttribute { + return node.kind === SyntaxKind.JsxSpreadAttribute; + } + + export function isJsxExpression(node: Node): node is JsxExpression { + return node.kind === SyntaxKind.JsxExpression; + } + + // Clauses + + export function isCaseClause(node: Node): node is CaseClause { + return node.kind === SyntaxKind.CaseClause; + } + + export function isDefaultClause(node: Node): node is DefaultClause { + return node.kind === SyntaxKind.DefaultClause; + } + + export function isHeritageClause(node: Node): node is HeritageClause { + return node.kind === SyntaxKind.HeritageClause; + } + + export function isCatchClause(node: Node): node is CatchClause { + return node.kind === SyntaxKind.CatchClause; + } + + // Property assignments + + export function isPropertyAssignment(node: Node): node is PropertyAssignment { + return node.kind === SyntaxKind.PropertyAssignment; + } + + export function isShorthandPropertyAssignment(node: Node): node is ShorthandPropertyAssignment { + return node.kind === SyntaxKind.ShorthandPropertyAssignment; + } + + export function isSpreadAssignment(node: Node): node is SpreadAssignment { + return node.kind === SyntaxKind.SpreadAssignment; + } + + // Enum + + export function isEnumMember(node: Node): node is EnumMember { + return node.kind === SyntaxKind.EnumMember; + } + + // Top-level nodes + export function isSourceFile(node: Node): node is SourceFile { + return node.kind === SyntaxKind.SourceFile; + } + + export function isBundle(node: Node): node is Bundle { + return node.kind === SyntaxKind.Bundle; + } + + // JSDoc + + export function isJSDocTypeExpression(node: Node): node is JSDocTypeExpression { + return node.kind === SyntaxKind.JSDocTypeExpression; + } + + export function isJSDocAllType(node: JSDocAllType): node is JSDocAllType { + return node.kind === SyntaxKind.JSDocAllType; + } + + export function isJSDocUnknownType(node: Node): node is JSDocUnknownType { + return node.kind === SyntaxKind.JSDocUnknownType; + } + + export function isJSDocArrayType(node: Node): node is JSDocArrayType { + return node.kind === SyntaxKind.JSDocArrayType; + } + + export function isJSDocUnionType(node: Node): node is JSDocUnionType { + return node.kind === SyntaxKind.JSDocUnionType; + } + + export function isJSDocTupleType(node: Node): node is JSDocTupleType { + return node.kind === SyntaxKind.JSDocTupleType; + } + + export function isJSDocNullableType(node: Node): node is JSDocNullableType { + return node.kind === SyntaxKind.JSDocNullableType; + } + + export function isJSDocNonNullableType(node: Node): node is JSDocNonNullableType { + return node.kind === SyntaxKind.JSDocNonNullableType; + } + + export function isJSDocRecordType(node: Node): node is JSDocRecordType { + return node.kind === SyntaxKind.JSDocRecordType; + } + + export function isJSDocRecordMember(node: Node): node is JSDocRecordMember { + return node.kind === SyntaxKind.JSDocRecordMember; + } + + export function isJSDocTypeReference(node: Node): node is JSDocTypeReference { + return node.kind === SyntaxKind.JSDocTypeReference; + } + + export function isJSDocOptionalType(node: Node): node is JSDocOptionalType { + return node.kind === SyntaxKind.JSDocOptionalType; + } + + export function isJSDocFunctionType(node: Node): node is JSDocFunctionType { + return node.kind === SyntaxKind.JSDocFunctionType; + } + + export function isJSDocVariadicType(node: Node): node is JSDocVariadicType { + return node.kind === SyntaxKind.JSDocVariadicType; + } + + export function isJSDocConstructorType(node: Node): node is JSDocConstructorType { + return node.kind === SyntaxKind.JSDocConstructorType; + } + + export function isJSDocThisType(node: Node): node is JSDocThisType { + return node.kind === SyntaxKind.JSDocThisType; + } + + export function isJSDoc(node: Node): node is JSDoc { + return node.kind === SyntaxKind.JSDocComment; + } + + export function isJSDocAugmentsTag(node: Node): node is JSDocAugmentsTag { + return node.kind === SyntaxKind.JSDocAugmentsTag; + } + + export function isJSDocParameterTag(node: Node): node is JSDocParameterTag { + return node.kind === SyntaxKind.JSDocParameterTag; + } + + export function isJSDocReturnTag(node: Node): node is JSDocReturnTag { + return node.kind === SyntaxKind.JSDocReturnTag; + } + + export function isJSDocTypeTag(node: Node): node is JSDocTypeTag { + return node.kind === SyntaxKind.JSDocTypeTag; + } + + export function isJSDocTemplateTag(node: Node): node is JSDocTemplateTag { + return node.kind === SyntaxKind.JSDocTemplateTag; + } + + export function isJSDocTypedefTag(node: Node): node is JSDocTypedefTag { + return node.kind === SyntaxKind.JSDocTypedefTag; + } + + export function isJSDocPropertyTag(node: Node): node is JSDocPropertyTag { + return node.kind === SyntaxKind.JSDocPropertyTag; + } + + export function isJSDocTypeLiteral(node: Node): node is JSDocTypeLiteral { + return node.kind === SyntaxKind.JSDocTypeLiteral; + } + + export function isJSDocLiteralType(node: Node): node is JSDocLiteralType { + return node.kind === SyntaxKind.JSDocLiteralType; + } +} + +// Node tests +// +// All node tests in the following list should *not* reference parent pointers so that +// they may be used with transformations. +namespace ts { + /** + * True if node is of some token syntax kind. + * For example, this is true for an IfKeyword but not for an IfStatement. + */ + export function isToken(n: Node): boolean { + return n.kind >= SyntaxKind.FirstToken && n.kind <= SyntaxKind.LastToken; + } + + // Node Arrays + + /* @internal */ + export function isNodeArray(array: T[]): array is NodeArray { + return array.hasOwnProperty("pos") + && array.hasOwnProperty("end"); + } + + // Literals + + /* @internal */ + export function isLiteralKind(kind: SyntaxKind): boolean { + return SyntaxKind.FirstLiteralToken <= kind && kind <= SyntaxKind.LastLiteralToken; + } + + export function isLiteralExpression(node: Node): node is LiteralExpression { + return isLiteralKind(node.kind); + } + + // Pseudo-literals + + /* @internal */ + export function isTemplateLiteralKind(kind: SyntaxKind): boolean { + return SyntaxKind.FirstTemplateToken <= kind && kind <= SyntaxKind.LastTemplateToken; + } + + export function isTemplateMiddleOrTemplateTail(node: Node): node is TemplateMiddle | TemplateTail { + const kind = node.kind; + return kind === SyntaxKind.TemplateMiddle + || kind === SyntaxKind.TemplateTail; + } + + // Identifiers + + /* @internal */ + export function isGeneratedIdentifier(node: Node): node is GeneratedIdentifier { + // Using `>` here catches both `GeneratedIdentifierKind.None` and `undefined`. + return isIdentifier(node) && node.autoGenerateKind > GeneratedIdentifierKind.None; + } + + // Keywords + + /* @internal */ + export function isModifierKind(token: SyntaxKind): boolean { + switch (token) { + case SyntaxKind.AbstractKeyword: + case SyntaxKind.AsyncKeyword: + case SyntaxKind.ConstKeyword: + case SyntaxKind.DeclareKeyword: + case SyntaxKind.DefaultKeyword: + case SyntaxKind.ExportKeyword: + case SyntaxKind.PublicKeyword: + case SyntaxKind.PrivateKeyword: + case SyntaxKind.ProtectedKeyword: + case SyntaxKind.ReadonlyKeyword: + case SyntaxKind.StaticKeyword: + return true; + } + return false; + } + + export function isModifier(node: Node): node is Modifier { + return isModifierKind(node.kind); + } + + export function isEntityName(node: Node): node is EntityName { + const kind = node.kind; + return kind === SyntaxKind.QualifiedName + || kind === SyntaxKind.Identifier; + } + + export function isPropertyName(node: Node): node is PropertyName { + const kind = node.kind; + return kind === SyntaxKind.Identifier + || kind === SyntaxKind.StringLiteral + || kind === SyntaxKind.NumericLiteral + || kind === SyntaxKind.ComputedPropertyName; + } + + export function isBindingName(node: Node): node is BindingName { + const kind = node.kind; + return kind === SyntaxKind.Identifier + || kind === SyntaxKind.ObjectBindingPattern + || kind === SyntaxKind.ArrayBindingPattern; + } + + // Functions + + export function isFunctionLike(node: Node): node is FunctionLikeDeclaration { + return node && isFunctionLikeKind(node.kind); + } + + /* @internal */ + export function isFunctionLikeKind(kind: SyntaxKind): boolean { + switch (kind) { + case SyntaxKind.Constructor: + case SyntaxKind.FunctionExpression: + case SyntaxKind.FunctionDeclaration: + case SyntaxKind.ArrowFunction: + case SyntaxKind.MethodDeclaration: + case SyntaxKind.MethodSignature: + case SyntaxKind.GetAccessor: + case SyntaxKind.SetAccessor: + case SyntaxKind.CallSignature: + case SyntaxKind.ConstructSignature: + case SyntaxKind.IndexSignature: + case SyntaxKind.FunctionType: + case SyntaxKind.ConstructorType: + return true; + } + + return false; + } + + // Classes + export function isClassElement(node: Node): node is ClassElement { + const kind = node.kind; + return kind === SyntaxKind.Constructor + || kind === SyntaxKind.PropertyDeclaration + || kind === SyntaxKind.MethodDeclaration + || kind === SyntaxKind.GetAccessor + || kind === SyntaxKind.SetAccessor + || kind === SyntaxKind.IndexSignature + || kind === SyntaxKind.SemicolonClassElement + || kind === SyntaxKind.MissingDeclaration; + } + + export function isClassLike(node: Node): node is ClassLikeDeclaration { + return node && (node.kind === SyntaxKind.ClassDeclaration || node.kind === SyntaxKind.ClassExpression); + } + + export function isAccessor(node: Node): node is AccessorDeclaration { + return node && (node.kind === SyntaxKind.GetAccessor || node.kind === SyntaxKind.SetAccessor); + } + + // Type members + + export function isTypeElement(node: Node): node is TypeElement { + const kind = node.kind; + return kind === SyntaxKind.ConstructSignature + || kind === SyntaxKind.CallSignature + || kind === SyntaxKind.PropertySignature + || kind === SyntaxKind.MethodSignature + || kind === SyntaxKind.IndexSignature + || kind === SyntaxKind.MissingDeclaration; + } + + export function isObjectLiteralElementLike(node: Node): node is ObjectLiteralElementLike { + const kind = node.kind; + return kind === SyntaxKind.PropertyAssignment + || kind === SyntaxKind.ShorthandPropertyAssignment + || kind === SyntaxKind.SpreadAssignment + || kind === SyntaxKind.MethodDeclaration + || kind === SyntaxKind.GetAccessor + || kind === SyntaxKind.SetAccessor + || kind === SyntaxKind.MissingDeclaration; + } + + // Type + + function isTypeNodeKind(kind: SyntaxKind) { + return (kind >= SyntaxKind.FirstTypeNode && kind <= SyntaxKind.LastTypeNode) + || kind === SyntaxKind.AnyKeyword + || kind === SyntaxKind.NumberKeyword + || kind === SyntaxKind.ObjectKeyword + || kind === SyntaxKind.BooleanKeyword + || kind === SyntaxKind.StringKeyword + || kind === SyntaxKind.SymbolKeyword + || kind === SyntaxKind.ThisKeyword + || kind === SyntaxKind.VoidKeyword + || kind === SyntaxKind.UndefinedKeyword + || kind === SyntaxKind.NullKeyword + || kind === SyntaxKind.NeverKeyword + || kind === SyntaxKind.ExpressionWithTypeArguments; + } + + /** + * Node test that determines whether a node is a valid type node. + * This differs from the `isPartOfTypeNode` function which determines whether a node is *part* + * of a TypeNode. + */ + export function isTypeNode(node: Node): node is TypeNode { + return isTypeNodeKind(node.kind); + } + + export function isFunctionOrConstructorTypeNode(node: Node): node is FunctionTypeNode | ConstructorTypeNode { + switch (node.kind) { + case SyntaxKind.FunctionType: + case SyntaxKind.ConstructorType: + return true; + } + + return false; + } + + // Binding patterns + + /* @internal */ + export function isBindingPattern(node: Node): node is BindingPattern { + if (node) { + const kind = node.kind; + return kind === SyntaxKind.ArrayBindingPattern + || kind === SyntaxKind.ObjectBindingPattern; + } + + return false; + } + + /* @internal */ + export function isAssignmentPattern(node: Node): node is AssignmentPattern { + const kind = node.kind; + return kind === SyntaxKind.ArrayLiteralExpression + || kind === SyntaxKind.ObjectLiteralExpression; + } + + + /* @internal */ + export function isArrayBindingElement(node: Node): node is ArrayBindingElement { + const kind = node.kind; + return kind === SyntaxKind.BindingElement + || kind === SyntaxKind.OmittedExpression; + } + + + /** + * Determines whether the BindingOrAssignmentElement is a BindingElement-like declaration + */ + /* @internal */ + export function isDeclarationBindingElement(bindingElement: BindingOrAssignmentElement): bindingElement is VariableDeclaration | ParameterDeclaration | BindingElement { + switch (bindingElement.kind) { + case SyntaxKind.VariableDeclaration: + case SyntaxKind.Parameter: + case SyntaxKind.BindingElement: + return true; + } + + return false; + } + + /** + * Determines whether a node is a BindingOrAssignmentPattern + */ + /* @internal */ + export function isBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is BindingOrAssignmentPattern { + return isObjectBindingOrAssignmentPattern(node) + || isArrayBindingOrAssignmentPattern(node); + } + + /** + * Determines whether a node is an ObjectBindingOrAssignmentPattern + */ + /* @internal */ + export function isObjectBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is ObjectBindingOrAssignmentPattern { + switch (node.kind) { + case SyntaxKind.ObjectBindingPattern: + case SyntaxKind.ObjectLiteralExpression: + return true; + } + + return false; + } + + /** + * Determines whether a node is an ArrayBindingOrAssignmentPattern + */ + /* @internal */ + export function isArrayBindingOrAssignmentPattern(node: BindingOrAssignmentElementTarget): node is ArrayBindingOrAssignmentPattern { + switch (node.kind) { + case SyntaxKind.ArrayBindingPattern: + case SyntaxKind.ArrayLiteralExpression: + return true; + } + + return false; + } + + // Expression + + export function isPropertyAccessOrQualifiedName(node: Node): node is PropertyAccessExpression | QualifiedName { + const kind = node.kind; + return kind === SyntaxKind.PropertyAccessExpression + || kind === SyntaxKind.QualifiedName; + } + + export function isCallLikeExpression(node: Node): node is CallLikeExpression { + switch (node.kind) { + case SyntaxKind.JsxOpeningElement: + case SyntaxKind.JsxSelfClosingElement: + case SyntaxKind.CallExpression: + case SyntaxKind.NewExpression: + case SyntaxKind.TaggedTemplateExpression: + case SyntaxKind.Decorator: + return true; + default: + return false; + } + } + + export function isCallOrNewExpression(node: Node): node is CallExpression | NewExpression { + return node.kind === SyntaxKind.CallExpression || node.kind === SyntaxKind.NewExpression; + } + + export function isTemplateLiteral(node: Node): node is TemplateLiteral { + const kind = node.kind; + return kind === SyntaxKind.TemplateExpression + || kind === SyntaxKind.NoSubstitutionTemplateLiteral; + } + + function isLeftHandSideExpressionKind(kind: SyntaxKind): boolean { + return kind === SyntaxKind.PropertyAccessExpression + || kind === SyntaxKind.ElementAccessExpression + || kind === SyntaxKind.NewExpression + || kind === SyntaxKind.CallExpression + || kind === SyntaxKind.JsxElement + || kind === SyntaxKind.JsxSelfClosingElement + || kind === SyntaxKind.TaggedTemplateExpression + || kind === SyntaxKind.ArrayLiteralExpression + || kind === SyntaxKind.ParenthesizedExpression + || kind === SyntaxKind.ObjectLiteralExpression + || kind === SyntaxKind.ClassExpression + || kind === SyntaxKind.FunctionExpression + || kind === SyntaxKind.Identifier + || kind === SyntaxKind.RegularExpressionLiteral + || kind === SyntaxKind.NumericLiteral + || kind === SyntaxKind.StringLiteral + || kind === SyntaxKind.NoSubstitutionTemplateLiteral + || kind === SyntaxKind.TemplateExpression + || kind === SyntaxKind.FalseKeyword + || kind === SyntaxKind.NullKeyword + || kind === SyntaxKind.ThisKeyword + || kind === SyntaxKind.TrueKeyword + || kind === SyntaxKind.SuperKeyword + || kind === SyntaxKind.NonNullExpression + || kind === SyntaxKind.MetaProperty; + } + + /* @internal */ + export function isLeftHandSideExpression(node: Node): node is LeftHandSideExpression { + return isLeftHandSideExpressionKind(skipPartiallyEmittedExpressions(node).kind); + } + + function isUnaryExpressionKind(kind: SyntaxKind): boolean { + return kind === SyntaxKind.PrefixUnaryExpression + || kind === SyntaxKind.PostfixUnaryExpression + || kind === SyntaxKind.DeleteExpression + || kind === SyntaxKind.TypeOfExpression + || kind === SyntaxKind.VoidExpression + || kind === SyntaxKind.AwaitExpression + || kind === SyntaxKind.TypeAssertionExpression + || isLeftHandSideExpressionKind(kind); + } + + /* @internal */ + export function isUnaryExpression(node: Node): node is UnaryExpression { + return isUnaryExpressionKind(skipPartiallyEmittedExpressions(node).kind); + } + + function isExpressionKind(kind: SyntaxKind) { + return kind === SyntaxKind.ConditionalExpression + || kind === SyntaxKind.YieldExpression + || kind === SyntaxKind.ArrowFunction + || kind === SyntaxKind.BinaryExpression + || kind === SyntaxKind.SpreadElement + || kind === SyntaxKind.AsExpression + || kind === SyntaxKind.OmittedExpression + || kind === SyntaxKind.CommaListExpression + || isUnaryExpressionKind(kind); + } + + /* @internal */ + export function isExpression(node: Node): node is Expression { + return isExpressionKind(skipPartiallyEmittedExpressions(node).kind); + } + + export function isAssertionExpression(node: Node): node is AssertionExpression { + const kind = node.kind; + return kind === SyntaxKind.TypeAssertionExpression + || kind === SyntaxKind.AsExpression; + } + + /* @internal */ + export function isPartiallyEmittedExpression(node: Node): node is PartiallyEmittedExpression { + return node.kind === SyntaxKind.PartiallyEmittedExpression; + } + + /* @internal */ + export function isNotEmittedStatement(node: Node): node is NotEmittedStatement { + return node.kind === SyntaxKind.NotEmittedStatement; + } + + /* @internal */ + export function isNotEmittedOrPartiallyEmittedNode(node: Node): node is NotEmittedStatement | PartiallyEmittedExpression { + return isNotEmittedStatement(node) + || isPartiallyEmittedExpression(node); + } + + // Statement + + export function isIterationStatement(node: Node, lookInLabeledStatements: boolean): node is IterationStatement { + switch (node.kind) { + case SyntaxKind.ForStatement: + case SyntaxKind.ForInStatement: + case SyntaxKind.ForOfStatement: + case SyntaxKind.DoStatement: + case SyntaxKind.WhileStatement: + return true; + case SyntaxKind.LabeledStatement: + return lookInLabeledStatements && isIterationStatement((node).statement, lookInLabeledStatements); + } + + return false; + } + + // Element + + /* @internal */ + export function isConciseBody(node: Node): node is ConciseBody { + return isBlock(node) + || isExpression(node); + } + + /* @internal */ + export function isFunctionBody(node: Node): node is FunctionBody { + return isBlock(node); + } + + /* @internal */ + export function isForInitializer(node: Node): node is ForInitializer { + return isVariableDeclarationList(node) + || isExpression(node); + } + + /* @internal */ + export function isModuleBody(node: Node): node is ModuleBody { + const kind = node.kind; + return kind === SyntaxKind.ModuleBlock + || kind === SyntaxKind.ModuleDeclaration + || kind === SyntaxKind.Identifier; + } + + /* @internal */ + export function isNamespaceBody(node: Node): node is NamespaceBody { + const kind = node.kind; + return kind === SyntaxKind.ModuleBlock + || kind === SyntaxKind.ModuleDeclaration; + } + + /* @internal */ + export function isJSDocNamespaceBody(node: Node): node is JSDocNamespaceBody { + const kind = node.kind; + return kind === SyntaxKind.Identifier + || kind === SyntaxKind.ModuleDeclaration; + } + + /* @internal */ + export function isNamedImportBindings(node: Node): node is NamedImportBindings { + const kind = node.kind; + return kind === SyntaxKind.NamedImports + || kind === SyntaxKind.NamespaceImport; + } + + /* @internal */ + export function isModuleOrEnumDeclaration(node: Node): node is ModuleDeclaration | EnumDeclaration { + return node.kind === SyntaxKind.ModuleDeclaration || node.kind === SyntaxKind.EnumDeclaration; + } + + function isDeclarationKind(kind: SyntaxKind) { + return kind === SyntaxKind.ArrowFunction + || kind === SyntaxKind.BindingElement + || kind === SyntaxKind.ClassDeclaration + || kind === SyntaxKind.ClassExpression + || kind === SyntaxKind.Constructor + || kind === SyntaxKind.EnumDeclaration + || kind === SyntaxKind.EnumMember + || kind === SyntaxKind.ExportSpecifier + || kind === SyntaxKind.FunctionDeclaration + || kind === SyntaxKind.FunctionExpression + || kind === SyntaxKind.GetAccessor + || kind === SyntaxKind.ImportClause + || kind === SyntaxKind.ImportEqualsDeclaration + || kind === SyntaxKind.ImportSpecifier + || kind === SyntaxKind.InterfaceDeclaration + || kind === SyntaxKind.JsxAttribute + || kind === SyntaxKind.MethodDeclaration + || kind === SyntaxKind.MethodSignature + || kind === SyntaxKind.ModuleDeclaration + || kind === SyntaxKind.NamespaceExportDeclaration + || kind === SyntaxKind.NamespaceImport + || kind === SyntaxKind.Parameter + || kind === SyntaxKind.PropertyAssignment + || kind === SyntaxKind.PropertyDeclaration + || kind === SyntaxKind.PropertySignature + || kind === SyntaxKind.SetAccessor + || kind === SyntaxKind.ShorthandPropertyAssignment + || kind === SyntaxKind.TypeAliasDeclaration + || kind === SyntaxKind.TypeParameter + || kind === SyntaxKind.VariableDeclaration + || kind === SyntaxKind.JSDocTypedefTag; + } + + function isDeclarationStatementKind(kind: SyntaxKind) { + return kind === SyntaxKind.FunctionDeclaration + || kind === SyntaxKind.MissingDeclaration + || kind === SyntaxKind.ClassDeclaration + || kind === SyntaxKind.InterfaceDeclaration + || kind === SyntaxKind.TypeAliasDeclaration + || kind === SyntaxKind.EnumDeclaration + || kind === SyntaxKind.ModuleDeclaration + || kind === SyntaxKind.ImportDeclaration + || kind === SyntaxKind.ImportEqualsDeclaration + || kind === SyntaxKind.ExportDeclaration + || kind === SyntaxKind.ExportAssignment + || kind === SyntaxKind.NamespaceExportDeclaration; + } + + function isStatementKindButNotDeclarationKind(kind: SyntaxKind) { + return kind === SyntaxKind.BreakStatement + || kind === SyntaxKind.ContinueStatement + || kind === SyntaxKind.DebuggerStatement + || kind === SyntaxKind.DoStatement + || kind === SyntaxKind.ExpressionStatement + || kind === SyntaxKind.EmptyStatement + || kind === SyntaxKind.ForInStatement + || kind === SyntaxKind.ForOfStatement + || kind === SyntaxKind.ForStatement + || kind === SyntaxKind.IfStatement + || kind === SyntaxKind.LabeledStatement + || kind === SyntaxKind.ReturnStatement + || kind === SyntaxKind.SwitchStatement + || kind === SyntaxKind.ThrowStatement + || kind === SyntaxKind.TryStatement + || kind === SyntaxKind.VariableStatement + || kind === SyntaxKind.WhileStatement + || kind === SyntaxKind.WithStatement + || kind === SyntaxKind.NotEmittedStatement + || kind === SyntaxKind.EndOfDeclarationMarker + || kind === SyntaxKind.MergeDeclarationMarker; + } + + /* @internal */ + export function isDeclaration(node: Node): node is NamedDeclaration { + return isDeclarationKind(node.kind); + } + + /* @internal */ + export function isDeclarationStatement(node: Node): node is DeclarationStatement { + return isDeclarationStatementKind(node.kind); + } + + /** + * Determines whether the node is a statement that is not also a declaration + */ + /* @internal */ + export function isStatementButNotDeclaration(node: Node): node is Statement { + return isStatementKindButNotDeclarationKind(node.kind); + } + + /* @internal */ + export function isStatement(node: Node): node is Statement { + const kind = node.kind; + return isStatementKindButNotDeclarationKind(kind) + || isDeclarationStatementKind(kind) + || kind === SyntaxKind.Block; + } + + // Module references + + /* @internal */ + export function isModuleReference(node: Node): node is ModuleReference { + const kind = node.kind; + return kind === SyntaxKind.ExternalModuleReference + || kind === SyntaxKind.QualifiedName + || kind === SyntaxKind.Identifier; + } + + // JSX + + /* @internal */ + export function isJsxTagNameExpression(node: Node): node is JsxTagNameExpression { + const kind = node.kind; + return kind === SyntaxKind.ThisKeyword + || kind === SyntaxKind.Identifier + || kind === SyntaxKind.PropertyAccessExpression; + } + + /* @internal */ + export function isJsxChild(node: Node): node is JsxChild { + const kind = node.kind; + return kind === SyntaxKind.JsxElement + || kind === SyntaxKind.JsxExpression + || kind === SyntaxKind.JsxSelfClosingElement + || kind === SyntaxKind.JsxText; + } + + /* @internal */ + export function isJsxAttributeLike(node: Node): node is JsxAttributeLike { + const kind = node.kind; + return kind === SyntaxKind.JsxAttribute + || kind === SyntaxKind.JsxSpreadAttribute; + } + + /* @internal */ + export function isStringLiteralOrJsxExpression(node: Node): node is StringLiteral | JsxExpression { + const kind = node.kind; + return kind === SyntaxKind.StringLiteral + || kind === SyntaxKind.JsxExpression; + } + + export function isJsxOpeningLikeElement(node: Node): node is JsxOpeningLikeElement { + const kind = node.kind; + return kind === SyntaxKind.JsxOpeningElement + || kind === SyntaxKind.JsxSelfClosingElement; + } + + // Clauses + + export function isCaseOrDefaultClause(node: Node): node is CaseOrDefaultClause { + const kind = node.kind; + return kind === SyntaxKind.CaseClause + || kind === SyntaxKind.DefaultClause; + } + + // JSDoc + + /** True if node is of some JSDoc syntax kind. */ + /* @internal */ + export function isJSDocNode(node: Node): boolean { + return node.kind >= SyntaxKind.FirstJSDocNode && node.kind <= SyntaxKind.LastJSDocNode; + } + + // TODO: determine what this does before making it public. + /* @internal */ + export function isJSDocTag(node: Node): boolean { + return node.kind >= SyntaxKind.FirstJSDocTagNode && node.kind <= SyntaxKind.LastJSDocTagNode; + } +} From a72b14f1b8a6d9925255f31a8dc9d98c3595b29a Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders Date: Wed, 31 May 2017 09:10:45 -0700 Subject: [PATCH 53/56] Stop spelling suggestions after 10 name errors Previously, spelling suggestions stopped after name-not-found errors led to 10 *suggestions*. This may never happen for a failed import, which is the most common case for lots of name-not-found errors. Now spelling suggestions stop after the 10th name-not-found errors, which is better for performance. --- src/compiler/checker.ts | 2 +- .../reference/parserRealSource11.errors.txt | 40 +++++++++---------- .../reference/parserRealSource13.errors.txt | 4 +- .../reference/parserRealSource7.errors.txt | 32 +++++++-------- .../reference/parserRealSource8.errors.txt | 4 +- .../reference/parserharness.errors.txt | 36 ++++++++--------- 6 files changed, 59 insertions(+), 59 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 9ff1c4b41b9..fec82008863 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -1095,13 +1095,13 @@ namespace ts { if (suggestedNameNotFoundMessage && suggestionCount < maximumSuggestionCount) { suggestion = getSuggestionForNonexistentSymbol(originalLocation, name, meaning); if (suggestion) { - suggestionCount++; error(errorLocation, suggestedNameNotFoundMessage, typeof nameArg === "string" ? nameArg : declarationNameToString(nameArg), suggestion); } } if (!suggestion) { error(errorLocation, nameNotFoundMessage, typeof nameArg === "string" ? nameArg : declarationNameToString(nameArg)); } + suggestionCount++; } } return undefined; diff --git a/tests/baselines/reference/parserRealSource11.errors.txt b/tests/baselines/reference/parserRealSource11.errors.txt index 26cb07614a5..598b447d965 100644 --- a/tests/baselines/reference/parserRealSource11.errors.txt +++ b/tests/baselines/reference/parserRealSource11.errors.txt @@ -46,7 +46,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(199,42): error tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(219,33): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(231,30): error TS2304: Cannot find name 'Emitter'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(231,48): error TS2304: Cannot find name 'TokenID'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(233,52): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(233,52): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(237,36): error TS2304: Cannot find name 'TypeFlow'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(251,21): error TS2304: Cannot find name 'Symbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(268,19): error TS2304: Cannot find name 'NodeType'. @@ -85,27 +85,27 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(427,22): error tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(441,30): error TS2304: Cannot find name 'Emitter'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(441,48): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(445,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(446,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(446,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(449,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(451,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(451,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(453,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(454,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(454,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(457,22): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(460,22): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(463,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(465,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(465,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(467,22): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(469,50): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(472,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(472,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(474,22): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(476,50): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(479,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(479,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(481,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(483,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(483,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(485,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(487,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(487,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(489,22): error TS2304: Cannot find name 'NodeType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(491,58): error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(491,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(494,22): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(496,58): error TS2304: Cannot find name 'TokenID'. tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(498,22): error TS2304: Cannot find name 'NodeType'. @@ -848,7 +848,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.recordSourceMappingStart(this); emitter.emitJavascriptList(this, null, TokenID.Semicolon, startLine, false, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. emitter.recordSourceMappingEnd(this); } @@ -1139,7 +1139,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error !!! error TS2304: Cannot find name 'NodeType'. emitter.emitJavascript(this.operand, TokenID.PlusPlus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. emitter.writeToOutput("++"); break; case NodeType.LogNot: @@ -1148,14 +1148,14 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.writeToOutput("!"); emitter.emitJavascript(this.operand, TokenID.Exclamation, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.DecPost: ~~~~~~~~ !!! error TS2304: Cannot find name 'NodeType'. emitter.emitJavascript(this.operand, TokenID.MinusMinus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. emitter.writeToOutput("--"); break; case NodeType.ObjectLit: @@ -1174,7 +1174,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.writeToOutput("~"); emitter.emitJavascript(this.operand, TokenID.Tilde, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.Neg: ~~~~~~~~ @@ -1187,7 +1187,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error } emitter.emitJavascript(this.operand, TokenID.Minus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.Pos: ~~~~~~~~ @@ -1200,7 +1200,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error } emitter.emitJavascript(this.operand, TokenID.Plus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.IncPre: ~~~~~~~~ @@ -1208,7 +1208,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.writeToOutput("++"); emitter.emitJavascript(this.operand, TokenID.PlusPlus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.DecPre: ~~~~~~~~ @@ -1216,7 +1216,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.writeToOutput("--"); emitter.emitJavascript(this.operand, TokenID.MinusMinus, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. break; case NodeType.Throw: ~~~~~~~~ @@ -1224,7 +1224,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource11.ts(2356,48): error emitter.writeToOutput("throw "); emitter.emitJavascript(this.operand, TokenID.Tilde, false); ~~~~~~~ -!!! error TS2552: Cannot find name 'TokenID'. Did you mean 'tokenId'? +!!! error TS2304: Cannot find name 'TokenID'. emitter.writeToOutput(";"); break; case NodeType.Typeof: diff --git a/tests/baselines/reference/parserRealSource13.errors.txt b/tests/baselines/reference/parserRealSource13.errors.txt index 35bdd1cbb62..a77c5762405 100644 --- a/tests/baselines/reference/parserRealSource13.errors.txt +++ b/tests/baselines/reference/parserRealSource13.errors.txt @@ -113,7 +113,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(123,26): error tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(123,39): error TS2304: Cannot find name 'AST'. tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(128,33): error TS2339: Property 'getAstWalkerFactory' does not exist on type 'typeof TypeScript'. tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(132,51): error TS2304: Cannot find name 'AST'. -tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(135,36): error TS2552: Cannot find name 'NodeType'. Did you mean 'nodeType'? +tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(135,36): error TS2304: Cannot find name 'NodeType'. ==== tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts (116 errors) ==== @@ -483,7 +483,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource13.ts(135,36): error var nodeType = ast.nodeType; var callbackString = (NodeType)._map[nodeType] + "Callback"; ~~~~~~~~ -!!! error TS2552: Cannot find name 'NodeType'. Did you mean 'nodeType'? +!!! error TS2304: Cannot find name 'NodeType'. if (callback[callbackString]) { return callback[callbackString](pre, ast); } diff --git a/tests/baselines/reference/parserRealSource7.errors.txt b/tests/baselines/reference/parserRealSource7.errors.txt index f98dd31dba9..7d9627d4823 100644 --- a/tests/baselines/reference/parserRealSource7.errors.txt +++ b/tests/baselines/reference/parserRealSource7.errors.txt @@ -11,11 +11,11 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(34,54): error TS tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(34,68): error TS2304: Cannot find name 'TypeCollectionContext'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(35,25): error TS2304: Cannot find name 'ValueLocation'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(36,30): error TS2304: Cannot find name 'TypeLink'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(41,17): error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(41,17): error TS2304: Cannot find name 'FieldSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(43,31): error TS2304: Cannot find name 'SymbolFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(43,54): error TS2304: Cannot find name 'SymbolFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(49,58): error TS2304: Cannot find name 'Type'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(50,29): error TS2552: Cannot find name 'Signature'. Did you mean 'signature'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(50,29): error TS2304: Cannot find name 'Signature'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(51,36): error TS2304: Cannot find name 'TypeLink'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(55,30): error TS2304: Cannot find name 'SignatureGroup'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(59,66): error TS2304: Cannot find name 'Type'. @@ -46,7 +46,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(154,27): error T tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(155,26): error TS2304: Cannot find name 'hasFlag'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(155,55): error TS2304: Cannot find name 'VarFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(165,28): error TS2304: Cannot find name 'ModuleType'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(169,26): error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(169,26): error TS2304: Cannot find name 'TypeSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(186,48): error TS2304: Cannot find name 'AST'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(186,61): error TS2304: Cannot find name 'AST'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(186,75): error TS2304: Cannot find name 'TypeCollectionContext'. @@ -81,8 +81,8 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(212,46): error T tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(212,64): error TS2304: Cannot find name 'DualStringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(212,88): error TS2304: Cannot find name 'StringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(212,111): error TS2304: Cannot find name 'StringHashTable'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(216,30): error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(231,72): error TS2552: Cannot find name 'NodeType'. Did you mean 'modType'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(216,30): error TS2304: Cannot find name 'TypeSymbol'. +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(231,72): error TS2304: Cannot find name 'NodeType'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(234,27): error TS2304: Cannot find name 'TypeSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(238,80): error TS2304: Cannot find name 'StringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(239,37): error TS2304: Cannot find name 'ScopedMembers'. @@ -142,7 +142,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(349,47): error T tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(349,65): error TS2304: Cannot find name 'DualStringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(349,89): error TS2304: Cannot find name 'StringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(349,112): error TS2304: Cannot find name 'StringHashTable'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(350,30): error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(350,30): error TS2304: Cannot find name 'TypeSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(360,37): error TS2304: Cannot find name 'SymbolFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(364,37): error TS2304: Cannot find name 'SymbolFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(368,37): error TS2304: Cannot find name 'SymbolFlags'. @@ -196,7 +196,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(476,57): error T tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(477,29): error TS2304: Cannot find name 'ValueLocation'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(478,29): error TS2304: Cannot find name 'hasFlag'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(478,55): error TS2304: Cannot find name 'VarFlags'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(480,21): error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(480,21): error TS2304: Cannot find name 'FieldSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(482,34): error TS2304: Cannot find name 'hasFlag'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(482,60): error TS2304: Cannot find name 'VarFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(492,30): error TS2304: Cannot find name 'getTypeLink'. @@ -218,7 +218,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(507,26): error T tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(507,52): error TS2304: Cannot find name 'ASTFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(518,22): error TS2304: Cannot find name 'FieldSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(531,29): error TS2304: Cannot find name 'ValueLocation'. -tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(533,21): error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(533,21): error TS2304: Cannot find name 'FieldSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(535,53): error TS2304: Cannot find name 'VarFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(535,75): error TS2304: Cannot find name 'VarFlags'. tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(539,38): error TS2304: Cannot find name 'SymbolFlags'. @@ -372,7 +372,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T var fieldSymbol = new FieldSymbol("prototype", ast.minChar, ~~~~~~~~~~~ -!!! error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +!!! error TS2304: Cannot find name 'FieldSymbol'. context.checker.locationInfo.unitIndex, true, field); fieldSymbol.flags |= (SymbolFlags.Property | SymbolFlags.BuiltIn); ~~~~~~~~~~~ @@ -389,7 +389,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T !!! error TS2304: Cannot find name 'Type'. var signature = new Signature(); ~~~~~~~~~ -!!! error TS2552: Cannot find name 'Signature'. Did you mean 'signature'? +!!! error TS2304: Cannot find name 'Signature'. signature.returnType = new TypeLink(); ~~~~~~~~ !!! error TS2304: Cannot find name 'TypeLink'. @@ -570,7 +570,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T typeSymbol = new TypeSymbol(importDecl.id.text, importDecl.minChar, ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? +!!! error TS2304: Cannot find name 'TypeSymbol'. context.checker.locationInfo.unitIndex, modType); typeSymbol.aliasLink = importDecl; @@ -687,7 +687,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T typeSymbol = new TypeSymbol(modName, moduleDecl.minChar, ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? +!!! error TS2304: Cannot find name 'TypeSymbol'. context.checker.locationInfo.unitIndex, modType); if (context.scopeChain.moduleDecl) { @@ -704,7 +704,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T else { if (symbol && symbol.declAST && symbol.declAST.nodeType != NodeType.ModuleDeclaration) { ~~~~~~~~ -!!! error TS2552: Cannot find name 'NodeType'. Did you mean 'modType'? +!!! error TS2304: Cannot find name 'NodeType'. context.checker.errorReporter.simpleError(moduleDecl, "Conflicting symbol name for module '" + modName + "'"); } typeSymbol = symbol; @@ -943,7 +943,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T !!! error TS2304: Cannot find name 'StringHashTable'. typeSymbol = new TypeSymbol(className, classDecl.minChar, ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeSymbol'. Did you mean 'typeSymbol'? +!!! error TS2304: Cannot find name 'TypeSymbol'. context.checker.locationInfo.unitIndex, classType); typeSymbol.declAST = classDecl; typeSymbol.instanceType = instanceType; @@ -1181,7 +1181,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T var fieldSymbol = new FieldSymbol(argDecl.id.text, argDecl.minChar, ~~~~~~~~~~~ -!!! error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +!!! error TS2304: Cannot find name 'FieldSymbol'. context.checker.locationInfo.unitIndex, !hasFlag(argDecl.varFlags, VarFlags.Readonly), ~~~~~~~ @@ -1278,7 +1278,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource7.ts(828,13): error T var fieldSymbol = new FieldSymbol(varDecl.id.text, varDecl.minChar, ~~~~~~~~~~~ -!!! error TS2552: Cannot find name 'FieldSymbol'. Did you mean 'fieldSymbol'? +!!! error TS2304: Cannot find name 'FieldSymbol'. context.checker.locationInfo.unitIndex, (varDecl.varFlags & VarFlags.Readonly) == VarFlags.None, ~~~~~~~~ diff --git a/tests/baselines/reference/parserRealSource8.errors.txt b/tests/baselines/reference/parserRealSource8.errors.txt index a7a2b968baf..9f536cf6c7c 100644 --- a/tests/baselines/reference/parserRealSource8.errors.txt +++ b/tests/baselines/reference/parserRealSource8.errors.txt @@ -47,7 +47,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(160,52): error T tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(160,76): error TS2304: Cannot find name 'StringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(160,99): error TS2304: Cannot find name 'StringHashTable'. tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(162,28): error TS2304: Cannot find name 'Type'. -tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(163,30): error TS2552: Cannot find name 'WithSymbol'. Did you mean 'withSymbol'? +tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(163,30): error TS2304: Cannot find name 'WithSymbol'. tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(170,40): error TS2339: Property 'SymbolScopeBuilder' does not exist on type 'typeof TypeScript'. tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(176,50): error TS2304: Cannot find name 'AST'. tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(177,25): error TS2304: Cannot find name 'FuncDecl'. @@ -397,7 +397,7 @@ tests/cases/conformance/parser/ecmascript5/parserRealSource8.ts(454,35): error T !!! error TS2304: Cannot find name 'Type'. var withSymbol = new WithSymbol(withStmt.minChar, context.typeFlow.checker.locationInfo.unitIndex, withType); ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'WithSymbol'. Did you mean 'withSymbol'? +!!! error TS2304: Cannot find name 'WithSymbol'. withType.members = members; withType.ambientMembers = ambientMembers; withType.symbol = withSymbol; diff --git a/tests/baselines/reference/parserharness.errors.txt b/tests/baselines/reference/parserharness.errors.txt index e7c83f0a058..5ec35021fef 100644 --- a/tests/baselines/reference/parserharness.errors.txt +++ b/tests/baselines/reference/parserharness.errors.txt @@ -18,17 +18,17 @@ tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(721,62): e tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(724,29): error TS2304: Cannot find name 'ITextWriter'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(754,53): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(764,56): error TS2503: Cannot find namespace 'TypeScript'. -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(765,37): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(767,47): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(776,13): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(776,42): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(765,37): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(767,47): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(776,13): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(776,42): error TS2304: Cannot find name 'TypeScript'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(781,23): error TS2503: Cannot find namespace 'TypeScript'. -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(794,49): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(795,49): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,53): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,89): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(794,49): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(795,49): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,53): error TS2304: Cannot find name 'TypeScript'. +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,89): error TS2304: Cannot find name 'TypeScript'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,115): error TS2503: Cannot find namespace 'TypeScript'. -tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,145): error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(987,145): error TS2304: Cannot find name 'TypeScript'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(988,43): error TS2304: Cannot find name 'TypeScript'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(999,40): error TS2503: Cannot find namespace 'TypeScript'. tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(1041,43): error TS2503: Cannot find namespace 'TypeScript'. @@ -917,11 +917,11 @@ tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(2030,32): !!! error TS2503: Cannot find namespace 'TypeScript'. var compiler = c || new TypeScript.TypeScriptCompiler(stderr); ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. compiler.parser.errorRecovery = true; compiler.settings.codeGenTarget = TypeScript.CodeGenTarget.ES5; ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. compiler.settings.controlFlow = true; compiler.settings.controlFlowUseDef = true; if (Harness.usePull) { @@ -932,9 +932,9 @@ tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(2030,32): compiler.parseEmitOption(stdout); TypeScript.moduleGenTarget = TypeScript.ModuleGenTarget.Synchronous; ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. compiler.addUnit(Harness.Compiler.libText, "lib.d.ts", true); return compiler; } @@ -956,10 +956,10 @@ tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(2030,32): // requires unit to already exist in the compiler compiler.pullUpdateUnit(new TypeScript.StringSourceText(""), filename, true); ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. compiler.pullUpdateUnit(new TypeScript.StringSourceText(code), filename, true); ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. } } else { @@ -1153,13 +1153,13 @@ tests/cases/conformance/parser/ecmascript5/RealWorld/parserharness.ts(2030,32): var script = compiler.scripts.members[m]; var enclosingScopeContext = TypeScript.findEnclosingScopeAt(new TypeScript.NullLogger(), script, new TypeScript.StringSourceText(code), 0, false); ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. ~~~~~~~~~~ !!! error TS2503: Cannot find namespace 'TypeScript'. ~~~~~~~~~~ -!!! error TS2552: Cannot find name 'TypeScript'. Did you mean 'TypeScriptLS'? +!!! error TS2304: Cannot find name 'TypeScript'. var entries = new TypeScript.ScopeTraversal(compiler).getScopeEntries(enclosingScopeContext); ~~~~~~~~~~ !!! error TS2304: Cannot find name 'TypeScript'. From 315b72d035a60ef23443c748032220dfc92ce222 Mon Sep 17 00:00:00 2001 From: Andy Date: Wed, 31 May 2017 15:31:35 -0700 Subject: [PATCH 54/56] Use `it` instead of `describe` for tests (#16172) * Use `it` instead of `describe` for tests * Create SourceFiles lazily * Use before() hooks --- src/harness/unittests/printer.ts | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/harness/unittests/printer.ts b/src/harness/unittests/printer.ts index a9af46b2780..4bdafe04ba1 100644 --- a/src/harness/unittests/printer.ts +++ b/src/harness/unittests/printer.ts @@ -14,7 +14,9 @@ namespace ts { describe("printFile", () => { const printsCorrectly = makePrintsCorrectly("printsFileCorrectly"); - const sourceFile = createSourceFile("source.ts", ` + // Avoid eagerly creating the sourceFile so that `createSourceFile` doesn't run unless one of these tests is run. + let sourceFile: SourceFile; + before(() => sourceFile = createSourceFile("source.ts", ` interface A { // comment1 readonly prop?: T; @@ -48,8 +50,7 @@ namespace ts { // comment10 function functionWithDefaultArgValue(argument: string = "defaultValue"): void { } - `, ScriptTarget.ES2015); - + `, ScriptTarget.ES2015)); printsCorrectly("default", {}, printer => printer.printFile(sourceFile)); printsCorrectly("removeComments", { removeComments: true }, printer => printer.printFile(sourceFile)); @@ -59,7 +60,8 @@ namespace ts { describe("printBundle", () => { const printsCorrectly = makePrintsCorrectly("printsBundleCorrectly"); - const bundle = createBundle([ + let bundle: Bundle; + before(() => bundle = createBundle([ createSourceFile("a.ts", ` /*! [a.ts] */ @@ -72,14 +74,15 @@ namespace ts { // comment1 const b = 2; `, ScriptTarget.ES2015) - ]); + ])); printsCorrectly("default", {}, printer => printer.printBundle(bundle)); printsCorrectly("removeComments", { removeComments: true }, printer => printer.printBundle(bundle)); }); describe("printNode", () => { const printsCorrectly = makePrintsCorrectly("printsNodeCorrectly"); - const sourceFile = createSourceFile("source.ts", "", ScriptTarget.ES2015); + let sourceFile: SourceFile; + before(() => sourceFile = createSourceFile("source.ts", "", ScriptTarget.ES2015)); // tslint:disable boolean-trivia const syntheticNode = createClassDeclaration( undefined, From 6e49237d31435c9aea8ac6f8e8aa4fdad353eaab Mon Sep 17 00:00:00 2001 From: t_ Date: Fri, 2 Jun 2017 05:43:44 +0900 Subject: [PATCH 55/56] Remove trailing whitespace from tsconfig.json (#16197) * Remove trailing whitespace from tsconfig.json * Simplify --- src/compiler/commandLineParser.ts | 2 +- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- .../tsconfig.json | 22 +++++++++---------- 9 files changed, 89 insertions(+), 89 deletions(-) diff --git a/src/compiler/commandLineParser.ts b/src/compiler/commandLineParser.ts index e612378671d..fa0c8140bb6 100644 --- a/src/compiler/commandLineParser.ts +++ b/src/compiler/commandLineParser.ts @@ -1042,7 +1042,7 @@ namespace ts { for (let i = 0; i < nameColumn.length; i++) { const optionName = nameColumn[i]; const description = descriptionColumn[i]; - result.push(tab + tab + optionName + makePadding(marginLength - optionName.length + 2) + description); + result.push(optionName && `${tab}${tab}${optionName}${ description && (makePadding(marginLength - optionName.length + 2) + description)}`); } if (configurations.files && configurations.files.length) { result.push(`${tab}},`); diff --git a/tests/baselines/reference/tsConfig/Default initialized TSConfig/tsconfig.json b/tests/baselines/reference/tsConfig/Default initialized TSConfig/tsconfig.json index 97f59dea8ea..04599005244 100644 --- a/tests/baselines/reference/tsConfig/Default initialized TSConfig/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Default initialized TSConfig/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with boolean value compiler options/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with boolean value compiler options/tsconfig.json index b90e3fc6c58..2a41e2c4df0 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with boolean value compiler options/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with boolean value compiler options/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true, /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ "noUnusedLocals": true /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with enum value compiler options/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with enum value compiler options/tsconfig.json index 482cfa6a9d5..e29a2813282 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with enum value compiler options/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with enum value compiler options/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with files options/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with files options/tsconfig.json index c6a26629dab..69831916904 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with files options/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with files options/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ }, diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option value/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option value/tsconfig.json index 72289dd1787..407df036f89 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option value/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option value/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ "lib": ["es5","es2015.promise"], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option/tsconfig.json index 97f59dea8ea..04599005244 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with incorrect compiler option/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options with enum value/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options with enum value/tsconfig.json index 1ac7c8c54da..e4d0b37ae51 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options with enum value/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options with enum value/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ "lib": ["es5","es2015.core"], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ // "types": [], /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } diff --git a/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options/tsconfig.json b/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options/tsconfig.json index 33a9ecc5cd4..3e3f7a85b34 100644 --- a/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options/tsconfig.json +++ b/tests/baselines/reference/tsConfig/Initialized TSConfig with list compiler options/tsconfig.json @@ -1,6 +1,6 @@ { "compilerOptions": { - /* Basic Options */ + /* Basic Options */ "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */ // "lib": [], /* Specify library files to be included in the compilation: */ @@ -17,21 +17,21 @@ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ - - /* Strict Type-Checking Options */ + + /* Strict Type-Checking Options */ "strict": true, /* Enable all strict type-checking options. */ // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ // "strictNullChecks": true, /* Enable strict null checks. */ // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ - - /* Additional Checks */ + + /* Additional Checks */ // "noUnusedLocals": true, /* Report errors on unused locals. */ // "noUnusedParameters": true, /* Report errors on unused parameters. */ // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - - /* Module Resolution Options */ + + /* Module Resolution Options */ // "moduleResolution": "node", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ @@ -39,14 +39,14 @@ // "typeRoots": [], /* List of folders to include type definitions from. */ "types": ["jquery","mocha"] /* Type declaration files to be included in compilation. */ // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - - /* Source Map Options */ + + /* Source Map Options */ // "sourceRoot": "./", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ // "mapRoot": "./", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ - - /* Experimental Options */ + + /* Experimental Options */ // "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ } From b62e1b57455562da9b8e1d2ab102753400820c87 Mon Sep 17 00:00:00 2001 From: William Orr Date: Thu, 1 Jun 2017 18:27:20 -0700 Subject: [PATCH 56/56] Use unix cache location on the major BSDs (#16187) --- src/server/server.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/server/server.ts b/src/server/server.ts index 390a0f2f6f4..7e1ee683c8c 100644 --- a/src/server/server.ts +++ b/src/server/server.ts @@ -45,6 +45,8 @@ namespace ts.server { os.tmpdir(); return combinePaths(normalizeSlashes(basePath), "Microsoft/TypeScript"); } + case "openbsd": + case "freebsd": case "darwin": case "linux": case "android": {