diff --git a/src/compiler/diagnosticInformationMap.generated.ts b/src/compiler/diagnosticInformationMap.generated.ts index 622b28d5f18..739c2ea460f 100644 --- a/src/compiler/diagnosticInformationMap.generated.ts +++ b/src/compiler/diagnosticInformationMap.generated.ts @@ -486,6 +486,21 @@ module ts { Function_implicitly_has_return_type_any_because_it_does_not_have_a_return_type_annotation_and_is_referenced_directly_or_indirectly_in_one_of_its_return_expressions: { code: 7024, category: DiagnosticCategory.Error, key: "Function implicitly has return type 'any' because it does not have a return type annotation and is referenced directly or indirectly in one of its return expressions." }, You_cannot_rename_this_element: { code: 8000, category: DiagnosticCategory.Error, key: "You cannot rename this element." }, You_cannot_rename_elements_that_are_defined_in_the_standard_TypeScript_library: { code: 8001, category: DiagnosticCategory.Error, key: "You cannot rename elements that are defined in the standard TypeScript library." }, + import_can_only_be_used_in_TypeScript: { code: 8002, category: DiagnosticCategory.Error, key: "'import ... =' can only be used in TypeScript." }, + export_can_only_be_used_in_TypeScript: { code: 8003, category: DiagnosticCategory.Error, key: "'export=' can only be used in TypeScript." }, + type_parameter_declarations_can_only_be_used_in_TypeScript: { code: 8004, category: DiagnosticCategory.Error, key: "'type parameter declarations' can only be used in TypeScript." }, + implements_clauses_can_only_be_used_in_TypeScript: { code: 8005, category: DiagnosticCategory.Error, key: "'implements clauses' can only be used in TypeScript." }, + interface_declarations_can_only_be_used_in_TypeScript: { code: 8006, category: DiagnosticCategory.Error, key: "'interface declarations' can only be used in TypeScript." }, + module_declarations_can_only_be_used_in_TypeScript: { code: 8007, category: DiagnosticCategory.Error, key: "'module declarations' can only be used in TypeScript." }, + type_aliases_can_only_be_used_in_TypeScript: { code: 8007, category: DiagnosticCategory.Error, key: "'type aliases' can only be used in TypeScript." }, + _0_can_only_be_used_in_TypeScript: { code: 8008, category: DiagnosticCategory.Error, key: "'{0}' can only be used in TypeScript." }, + types_can_only_be_used_in_TypeScript: { code: 8009, category: DiagnosticCategory.Error, key: "'types' can only be used in TypeScript." }, + type_arguments_can_only_be_used_in_TypeScript: { code: 8010, category: DiagnosticCategory.Error, key: "'type arguments' can only be used in TypeScript." }, + parameter_modifiers_can_only_be_used_in_TypeScript: { code: 8011, category: DiagnosticCategory.Error, key: "'parameter modifiers' can only be used in TypeScript." }, + can_only_be_used_in_TypeScript: { code: 8012, category: DiagnosticCategory.Error, key: "'?' can only be used in TypeScript." }, + property_declarations_can_only_be_used_in_TypeScript: { code: 8013, category: DiagnosticCategory.Error, key: "'property declarations' can only be used in TypeScript." }, + enum_declarations_can_only_be_used_in_TypeScript: { code: 8014, category: DiagnosticCategory.Error, key: "'enum declarations' can only be used in TypeScript." }, + type_assertion_expressions_can_only_be_used_in_TypeScript: { code: 8014, category: DiagnosticCategory.Error, key: "'type assertion expressions' can only be used in TypeScript." }, yield_expressions_are_not_currently_supported: { code: 9000, category: DiagnosticCategory.Error, key: "'yield' expressions are not currently supported." }, Generators_are_not_currently_supported: { code: 9001, category: DiagnosticCategory.Error, key: "Generators are not currently supported." }, The_arguments_object_cannot_be_referenced_in_an_arrow_function_Consider_using_a_standard_function_expression: { code: 9002, category: DiagnosticCategory.Error, key: "The 'arguments' object cannot be referenced in an arrow function. Consider using a standard function expression." }, diff --git a/src/compiler/diagnosticMessages.json b/src/compiler/diagnosticMessages.json index 410cce54d17..552f1b04606 100644 --- a/src/compiler/diagnosticMessages.json +++ b/src/compiler/diagnosticMessages.json @@ -1938,6 +1938,67 @@ "category": "Error", "code": 8001 }, + "'import ... =' can only be used in TypeScript.": { + "category": "Error", + "code": 8002 + }, + "'export=' can only be used in TypeScript.": { + "category": "Error", + "code": 8003 + }, + "'type parameter declarations' can only be used in TypeScript.": { + "category": "Error", + "code": 8004 + }, + "'implements clauses' can only be used in TypeScript.": { + "category": "Error", + "code": 8005 + }, + "'interface declarations' can only be used in TypeScript.": { + "category": "Error", + "code": 8006 + }, + "'module declarations' can only be used in TypeScript.": { + "category": "Error", + "code": 8007 + }, + "'type aliases' can only be used in TypeScript.": { + "category": "Error", + "code": 8007 + }, + "'{0}' can only be used in TypeScript.": { + "category": "Error", + "code": 8008 + }, + "'types' can only be used in TypeScript.": { + "category": "Error", + "code": 8009 + }, + "'type arguments' can only be used in TypeScript.": { + "category": "Error", + "code": 8010 + }, + "'parameter modifiers' can only be used in TypeScript.": { + "category": "Error", + "code": 8011 + }, + "'?' can only be used in TypeScript.": { + "category": "Error", + "code": 8012 + }, + "'property declarations' can only be used in TypeScript.": { + "category": "Error", + "code": 8013 + }, + "'enum declarations' can only be used in TypeScript.": { + "category": "Error", + "code": 8014 + }, + "'type assertion expressions' can only be used in TypeScript.": { + "category": "Error", + "code": 8014 + }, + "'yield' expressions are not currently supported.": { "category": "Error", "code": 9000 diff --git a/src/services/services.ts b/src/services/services.ts index 1bf5f6336d4..88a56a850cb 100644 --- a/src/services/services.ts +++ b/src/services/services.ts @@ -2370,15 +2370,25 @@ module ts { return program.getSyntacticDiagnostics(getValidSourceFile(fileName)); } + function isJavaScript(fileName: string) { + return fileExtensionIs(fileName, ".tsjs"); + } + /** * getSemanticDiagnostiscs return array of Diagnostics. If '-d' is not enabled, only report semantic errors * If '-d' enabled, report both semantic and emitter errors */ - function getSemanticDiagnostics(fileName: string) { + function getSemanticDiagnostics(fileName: string): Diagnostic[] { synchronizeHostData(); let targetSourceFile = getValidSourceFile(fileName); + // For JavaScript files, we don't want to report the normal typescript semantic errors. + // Instead, we just report errors for using TypeScript + if (isJavaScript(fileName)) { + return getJavaScriptSemanticDiagnostics(targetSourceFile); + } + // Only perform the action per file regardless of '-out' flag as LanguageServiceHost is expected to call this function per file. // Therefore only get diagnostics for given file. @@ -2392,6 +2402,148 @@ module ts { return semanticDiagnostics.concat(declarationDiagnostics); } + function getJavaScriptSemanticDiagnostics(sourceFile: SourceFile): Diagnostic[] { + let diagnostics: Diagnostic[] = []; + walk(sourceFile); + + return diagnostics; + + function walk(node: Node) { + if (!node) { + return; + } + + switch (node.kind) { + case SyntaxKind.ImportEqualsDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.import_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.ExportAssignment: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.export_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.TypeParameter: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.type_parameter_declarations_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.ClassDeclaration: + let classDeclaration = node; + if (checkModifiers(classDeclaration.modifiers)) { + return; + } + break; + case SyntaxKind.HeritageClause: + let heritageClause = node; + if (heritageClause.token === SyntaxKind.ImplementsKeyword) { + diagnostics.push(createDiagnosticForNode(node, Diagnostics.implements_clauses_can_only_be_used_in_TypeScript)); + return; + } + break; + case SyntaxKind.InterfaceDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.interface_declarations_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.ModuleDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.module_declarations_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.TypeAliasDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.type_aliases_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.MethodDeclaration: + case SyntaxKind.MethodSignature: + case SyntaxKind.Constructor: + case SyntaxKind.GetAccessor: + case SyntaxKind.SetAccessor: + case SyntaxKind.FunctionExpression: + case SyntaxKind.FunctionDeclaration: + case SyntaxKind.ArrowFunction: + case SyntaxKind.FunctionDeclaration: + let functionDeclaration = node; + if (checkModifiers(functionDeclaration.modifiers) || + checkTypeAnnotation(functionDeclaration.type)) { + return; + } + break; + case SyntaxKind.VariableStatement: + let variableStatement = node; + if (checkModifiers(variableStatement.modifiers)) { + return; + } + break; + case SyntaxKind.VariableDeclaration: + let variableDeclaration = node; + if (checkTypeAnnotation(variableDeclaration.type)) { + return; + } + break; + case SyntaxKind.CallExpression: + case SyntaxKind.NewExpression: + let expression = node; + if (expression.typeArguments && expression.typeArguments.length > 0) { + diagnostics.push(createFileDiagnostic(sourceFile, expression.typeArguments.pos, expression.typeArguments.end, + Diagnostics.type_arguments_can_only_be_used_in_TypeScript)); + return; + } + break; + case SyntaxKind.Parameter: + let parameter = node; + if (parameter.modifiers) { + diagnostics.push(createFileDiagnostic(sourceFile, parameter.modifiers.pos, parameter.modifiers.end, + Diagnostics.parameter_modifiers_can_only_be_used_in_TypeScript)); + return; + } + if (parameter.questionToken) { + diagnostics.push(createDiagnosticForNode(parameter.questionToken, Diagnostics.can_only_be_used_in_TypeScript)); + return; + } + if (parameter.type) { + diagnostics.push(createDiagnosticForNode(parameter.type, Diagnostics.types_can_only_be_used_in_TypeScript)); + return; + } + break; + case SyntaxKind.PropertyDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.property_declarations_can_only_be_used_in_TypeScript)); + return + case SyntaxKind.EnumDeclaration: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.enum_declarations_can_only_be_used_in_TypeScript)); + return; + case SyntaxKind.TypeAssertionExpression: + diagnostics.push(createDiagnosticForNode(node, Diagnostics.type_assertion_expressions_can_only_be_used_in_TypeScript)); + return; + } + + forEachChild(node, walk); + } + + function checkTypeAnnotation(type: TypeNode): boolean { + if (type) { + diagnostics.push(createDiagnosticForNode(type, Diagnostics.types_can_only_be_used_in_TypeScript)); + return true; + } + + return false; + } + + function checkModifiers(modifiers: ModifiersArray): boolean { + if (modifiers) { + for (let modifier of modifiers) { + switch (modifier.kind) { + case SyntaxKind.PublicKeyword: + case SyntaxKind.PrivateKeyword: + case SyntaxKind.ProtectedKeyword: + case SyntaxKind.DeclareKeyword: + diagnostics.push(createDiagnosticForNode(modifier, Diagnostics._0_can_only_be_used_in_TypeScript, tokenToString(modifier.kind))); + return true; + + // These are all legal modifiers. + case SyntaxKind.StaticKeyword: + case SyntaxKind.ExportKeyword: + case SyntaxKind.ConstKeyword: + case SyntaxKind.DefaultKeyword: + } + } + } + + return false; + } + } + function getCompilerOptionsDiagnostics() { synchronizeHostData(); return program.getGlobalDiagnostics();