Merge pull request #14496 from Microsoft/checkJSFiles

Add support to report errors in js files
This commit is contained in:
Mohamed Hegazy
2017-03-27 21:52:29 -07:00
committed by GitHub
57 changed files with 763 additions and 55 deletions
+1 -1
View File
@@ -946,7 +946,7 @@ task("generate-code-coverage", ["tests", builtLocalDirectory], function () {
// Browser tests
var nodeServerOutFile = "tests/webTestServer.js";
var nodeServerInFile = "tests/webTestServer.ts";
compileFile(nodeServerOutFile, [nodeServerInFile], [builtLocalDirectory, tscFile], [], /*useBuiltCompiler:*/ true, { noOutFile: true });
compileFile(nodeServerOutFile, [nodeServerInFile], [builtLocalDirectory, tscFile], [], /*useBuiltCompiler:*/ true, { noOutFile: true, lib: "es6" });
desc("Runs browserify on run.js to produce a file suitable for running tests in the browser");
task("browserify", ["tests", builtLocalDirectory, nodeServerOutFile], function() {
+6
View File
@@ -153,6 +153,12 @@ namespace ts {
category: Diagnostics.Basic_Options,
description: Diagnostics.Allow_javascript_files_to_be_compiled
},
{
name: "checkJs",
type: "boolean",
category: Diagnostics.Basic_Options,
description: Diagnostics.Report_errors_in_js_files
},
{
name: "jsx",
type: createMapFromTemplate({
+4
View File
@@ -2360,4 +2360,8 @@ namespace ts {
return Extension.Jsx;
}
}
export function isCheckJsEnabledForFile(sourceFile: SourceFile, compilerOptions: CompilerOptions) {
return sourceFile.checkJsDirective ? sourceFile.checkJsDirective.enabled : compilerOptions.checkJs;
}
}
+22
View File
@@ -3480,6 +3480,24 @@
"category": "Message",
"code": 90017
},
"Disable checking for this file.": {
"category": "Message",
"code": 90018
},
"Ignore this error message.": {
"category": "Message",
"code": 90019
},
"Initialize property '{0}' in the constructor.": {
"category": "Message",
"code": 90020
},
"Initialize static property '{0}'.": {
"category": "Message",
"code": 90021
},
"Octal literal types must use ES2015 syntax. Use the syntax '{0}'.": {
"category": "Error",
"code": 8017
@@ -3487,5 +3505,9 @@
"Octal literals are not allowed in enums members initializer. Use the syntax '{0}'.": {
"category": "Error",
"code": 8018
},
"Report errors in .js files.": {
"category": "Message",
"code": 8019
}
}
+12
View File
@@ -5822,6 +5822,7 @@ namespace ts {
const typeReferenceDirectives: FileReference[] = [];
const amdDependencies: { path: string; name: string }[] = [];
let amdModuleName: string;
let checkJsDirective: CheckJsDirective = undefined;
// Keep scanning all the leading trivia in the file until we get to something that
// isn't trivia. Any single line comment will be analyzed to see if it is a
@@ -5883,6 +5884,16 @@ namespace ts {
amdDependencies.push(amdDependency);
}
}
const checkJsDirectiveRegEx = /^\/\/\/?\s*(@ts-check|@ts-nocheck)\s*$/gim;
const checkJsDirectiveMatchResult = checkJsDirectiveRegEx.exec(comment);
if (checkJsDirectiveMatchResult) {
checkJsDirective = {
enabled: compareStrings(checkJsDirectiveMatchResult[1], "@ts-check", /*ignoreCase*/ true) === Comparison.EqualTo,
end: range.end,
pos: range.pos
};
}
}
}
@@ -5890,6 +5901,7 @@ namespace ts {
sourceFile.typeReferenceDirectives = typeReferenceDirectives;
sourceFile.amdDependencies = amdDependencies;
sourceFile.moduleName = amdModuleName;
sourceFile.checkJsDirective = checkJsDirective;
}
function setExternalModuleIndicator(sourceFile: SourceFile) {
+35 -5
View File
@@ -4,6 +4,7 @@
namespace ts {
const emptyArray: any[] = [];
const ignoreDiagnosticCommentRegEx = /(^\s*$)|(^\s*\/\/\/?\s*(@ts-ignore)?)/;
export function findConfigFile(searchPath: string, fileExists: (fileName: string) => boolean, configName = "tsconfig.json"): string {
while (true) {
@@ -911,17 +912,42 @@ namespace ts {
Debug.assert(!!sourceFile.bindDiagnostics);
const bindDiagnostics = sourceFile.bindDiagnostics;
// For JavaScript files, we don't want to report semantic errors.
// Instead, we'll report errors for using TypeScript-only constructs from within a
// JavaScript file when we get syntactic diagnostics for the file.
const checkDiagnostics = isSourceFileJavaScript(sourceFile) ? [] : typeChecker.getDiagnostics(sourceFile, cancellationToken);
// For JavaScript files, we don't want to report semantic errors unless explicitly requested.
const includeCheckDiagnostics = !isSourceFileJavaScript(sourceFile) || isCheckJsEnabledForFile(sourceFile, options);
const checkDiagnostics = includeCheckDiagnostics ? typeChecker.getDiagnostics(sourceFile, cancellationToken) : [];
const fileProcessingDiagnosticsInFile = fileProcessingDiagnostics.getDiagnostics(sourceFile.fileName);
const programDiagnosticsInFile = programDiagnostics.getDiagnostics(sourceFile.fileName);
return bindDiagnostics.concat(checkDiagnostics, fileProcessingDiagnosticsInFile, programDiagnosticsInFile);
const diagnostics = bindDiagnostics.concat(checkDiagnostics, fileProcessingDiagnosticsInFile, programDiagnosticsInFile);
return isSourceFileJavaScript(sourceFile)
? filter(diagnostics, shouldReportDiagnostic)
: diagnostics;
});
}
/**
* Skip errors if previous line start with '// @ts-ignore' comment, not counting non-empty non-comment lines
*/
function shouldReportDiagnostic(diagnostic: Diagnostic) {
const { file, start } = diagnostic;
const lineStarts = getLineStarts(file);
let { line } = computeLineAndCharacterOfPosition(lineStarts, start);
while (line > 0) {
const previousLineText = file.text.slice(lineStarts[line - 1], lineStarts[line]);
const result = ignoreDiagnosticCommentRegEx.exec(previousLineText);
if (!result) {
// non-empty line
return true;
}
if (result[3]) {
// @ts-ignore
return false;
}
line--;
}
return true;
}
function getJavaScriptSyntacticDiagnosticsForFile(sourceFile: SourceFile): Diagnostic[] {
return runWithCancellationToken(() => {
const diagnostics: Diagnostic[] = [];
@@ -1722,6 +1748,10 @@ namespace ts {
programDiagnostics.add(createCompilerDiagnostic(Diagnostics.Option_0_cannot_be_specified_with_option_1, "allowJs", "declaration"));
}
if (options.checkJs && !options.allowJs) {
programDiagnostics.add(createCompilerDiagnostic(Diagnostics.Option_0_cannot_be_specified_without_specifying_option_1, "checkJs", "allowJs"));
}
if (options.emitDecoratorMetadata &&
!options.experimentalDecorators) {
programDiagnostics.add(createCompilerDiagnostic(Diagnostics.Option_0_cannot_be_specified_without_specifying_option_1, "emitDecoratorMetadata", "experimentalDecorators"));
+6
View File
@@ -1952,6 +1952,10 @@ namespace ts {
fileName: string;
}
export interface CheckJsDirective extends TextRange {
enabled: boolean;
}
export type CommentKind = SyntaxKind.SingleLineCommentTrivia | SyntaxKind.MultiLineCommentTrivia;
export interface CommentRange extends TextRange {
@@ -2294,6 +2298,7 @@ namespace ts {
/* @internal */ moduleAugmentations: LiteralExpression[];
/* @internal */ patternAmbientModules?: PatternAmbientModule[];
/* @internal */ ambientModuleNames: string[];
/* @internal */ checkJsDirective: CheckJsDirective | undefined;
}
export interface Bundle extends Node {
@@ -3355,6 +3360,7 @@ namespace ts {
alwaysStrict?: boolean; // Always combine with strict property
baseUrl?: string;
charset?: string;
checkJs?: boolean;
/* @internal */ configFilePath?: string;
declaration?: boolean;
declarationDir?: string;
+9
View File
@@ -2584,6 +2584,11 @@ namespace FourSlash {
}
}
public printAvailableCodeFixes() {
const codeFixes = this.getCodeFixActions(this.activeFile.fileName);
Harness.IO.log(stringify(codeFixes));
}
// Get the text of the entire line the caret is currently at
private getCurrentLineContent() {
const text = this.getFileContent(this.activeFile.fileName);
@@ -3772,6 +3777,10 @@ namespace FourSlashInterface {
this.state.printCompletionListMembers();
}
public printAvailableCodeFixes() {
this.state.printAvailableCodeFixes();
}
public printBreakpointLocation(pos: number) {
this.state.printBreakpointLocation(pos);
}
+1 -1
View File
@@ -191,7 +191,7 @@ namespace Utils {
for (const childName in node) {
if (childName === "parent" || childName === "nextContainer" || childName === "modifiers" || childName === "externalModuleIndicator" ||
// for now ignore jsdoc comments
childName === "jsDocComment") {
childName === "jsDocComment" || childName === "checkJsDirective") {
continue;
}
const child = (<any>node)[childName];
+2 -1
View File
@@ -1,4 +1,4 @@
{
{
"extends": "../tsconfig-base",
"compilerOptions": {
"removeComments": false,
@@ -81,6 +81,7 @@
"../services/codefixes/helpers.ts",
"../services/codefixes/importFixes.ts",
"../services/codefixes/unusedIdentifierFixes.ts",
"../services/codefixes/disableJsDiagnostics.ts",
"harness.ts",
"sourceMapRecorder.ts",
+2 -1
View File
@@ -31,7 +31,8 @@ namespace ts.server {
}
else {
// For configured projects, require that skipLibCheck be set also
return project.getCompilerOptions().skipLibCheck && project.isJsOnlyProject();
const options = project.getCompilerOptions();
return options.skipLibCheck && !options.checkJs && project.isJsOnlyProject();
}
}
@@ -0,0 +1,70 @@
/* @internal */
namespace ts.codefix {
registerCodeFix({
errorCodes: getApplicableDiagnosticCodes(),
getCodeActions: getDisableJsDiagnosticsCodeActions
});
function getApplicableDiagnosticCodes(): number[] {
const allDiagnostcs = <MapLike<DiagnosticMessage>>Diagnostics;
return Object.keys(allDiagnostcs)
.filter(d => allDiagnostcs[d] && allDiagnostcs[d].category === DiagnosticCategory.Error)
.map(d => allDiagnostcs[d].code);
}
function getIgnoreCommentLocationForLocation(sourceFile: SourceFile, position: number, newLineCharacter: string) {
const { line } = getLineAndCharacterOfPosition(sourceFile, position);
const lineStartPosition = getStartPositionOfLine(line, sourceFile);
const startPosition = getFirstNonSpaceCharacterPosition(sourceFile.text, lineStartPosition);
// First try to see if we can put the '// @ts-ignore' on the previous line.
// We need to make sure that we are not in the middle of a string literal or a comment.
// We also want to check if the previous line holds a comment for a node on the next line
// if so, we do not want to separate the node from its comment if we can.
if (!isInComment(sourceFile, startPosition) && !isInString(sourceFile, startPosition) && !isInTemplateString(sourceFile, startPosition)) {
const token = getTouchingToken(sourceFile, startPosition);
const tokenLeadingCommnets = getLeadingCommentRangesOfNode(token, sourceFile);
if (!tokenLeadingCommnets || !tokenLeadingCommnets.length || tokenLeadingCommnets[0].pos >= startPosition) {
return {
span: { start: startPosition, length: 0 },
newText: `// @ts-ignore${newLineCharacter}`
};
}
}
// If all fails, add an extra new line immediatlly before the error span.
return {
span: { start: position, length: 0 },
newText: `${position === startPosition ? "" : newLineCharacter}// @ts-ignore${newLineCharacter}`
};
}
function getDisableJsDiagnosticsCodeActions(context: CodeFixContext): CodeAction[] | undefined {
const { sourceFile, program, newLineCharacter, span } = context;
if (!isInJavaScriptFile(sourceFile) || !isCheckJsEnabledForFile(sourceFile, program.getCompilerOptions())) {
return undefined;
}
return [{
description: getLocaleSpecificMessage(Diagnostics.Ignore_this_error_message),
changes: [{
fileName: sourceFile.fileName,
textChanges: [getIgnoreCommentLocationForLocation(sourceFile, span.start, newLineCharacter)]
}]
},
{
description: getLocaleSpecificMessage(Diagnostics.Disable_checking_for_this_file),
changes: [{
fileName: sourceFile.fileName,
textChanges: [{
span: {
start: sourceFile.checkJsDirective ? sourceFile.checkJsDirective.pos : 0,
length: sourceFile.checkJsDirective ? sourceFile.checkJsDirective.end - sourceFile.checkJsDirective.pos : 0
},
newText: `// @ts-nocheck${newLineCharacter}`
}]
}]
}];
}
}
+98 -45
View File
@@ -18,68 +18,121 @@ namespace ts.codefix {
return undefined;
}
const classDeclaration = getContainingClass(token);
if (!classDeclaration) {
if (!isPropertyAccessExpression(token.parent) || token.parent.expression.kind !== SyntaxKind.ThisKeyword) {
return undefined;
}
if (!(token.parent && token.parent.kind === SyntaxKind.PropertyAccessExpression)) {
const classMemberDeclaration = getThisContainer(token, /*includeArrowFunctions*/ false);
if (!isClassElement(classMemberDeclaration)) {
return undefined;
}
if ((token.parent as PropertyAccessExpression).expression.kind !== SyntaxKind.ThisKeyword) {
const classDeclaration = <ClassLikeDeclaration>classMemberDeclaration.parent;
if (!classDeclaration || !isClassLike(classDeclaration)) {
return undefined;
}
let typeNode: TypeNode;
const isStatic = hasModifier(classMemberDeclaration, ModifierFlags.Static);
if (token.parent.parent.kind === SyntaxKind.BinaryExpression) {
const binaryExpression = token.parent.parent as BinaryExpression;
return isInJavaScriptFile(sourceFile) ? getActionsForAddMissingMemberInJavaScriptFile() : getActionsForAddMissingMemberInTypeScriptFile();
const checker = context.program.getTypeChecker();
const widenedType = checker.getWidenedType(checker.getBaseTypeOfLiteralType(checker.getTypeAtLocation(binaryExpression.right)));
typeNode = checker.typeToTypeNode(widenedType, classDeclaration) || typeNode;
function getActionsForAddMissingMemberInJavaScriptFile(): CodeAction[] | undefined {
const memberName = token.getText();
if (isStatic) {
if (classDeclaration.kind === SyntaxKind.ClassExpression) {
return undefined;
}
const className = classDeclaration.name.getText();
return [{
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Initialize_static_property_0), [memberName]),
changes: [{
fileName: sourceFile.fileName,
textChanges: [{
span: { start: classDeclaration.getEnd(), length: 0 },
newText: `${context.newLineCharacter}${className}.${memberName} = undefined;${context.newLineCharacter}`
}]
}]
}];
}
else {
const classConstructor = getFirstConstructorWithBody(classDeclaration);
if (!classConstructor) {
return undefined;
}
return [{
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Initialize_property_0_in_the_constructor), [memberName]),
changes: [{
fileName: sourceFile.fileName,
textChanges: [{
span: { start: classConstructor.body.getEnd() - 1, length: 0 },
newText: `this.${memberName} = undefined;${context.newLineCharacter}`
}]
}]
}];
}
}
typeNode = typeNode ? typeNode : createKeywordTypeNode(SyntaxKind.AnyKeyword);
function getActionsForAddMissingMemberInTypeScriptFile(): CodeAction[] | undefined {
let typeNode: TypeNode;
const openBrace = getOpenBraceOfClassLike(classDeclaration, sourceFile);
if (token.parent.parent.kind === SyntaxKind.BinaryExpression) {
const binaryExpression = token.parent.parent as BinaryExpression;
const property = createProperty(
/*decorators*/undefined,
/*modifiers*/ undefined,
token.getText(sourceFile),
/*questionToken*/ undefined,
typeNode,
/*initializer*/ undefined);
const propertyChangeTracker = textChanges.ChangeTracker.fromCodeFixContext(context);
propertyChangeTracker.insertNodeAfter(sourceFile, openBrace, property, { suffix: context.newLineCharacter });
const checker = context.program.getTypeChecker();
const widenedType = checker.getWidenedType(checker.getBaseTypeOfLiteralType(checker.getTypeAtLocation(binaryExpression.right)));
typeNode = checker.typeToTypeNode(widenedType, classDeclaration);
}
const stringTypeNode = createKeywordTypeNode(SyntaxKind.StringKeyword);
const indexingParameter = createParameter(
/*decorators*/ undefined,
/*modifiers*/ undefined,
/*dotDotDotToken*/ undefined,
"x",
/*questionToken*/ undefined,
stringTypeNode,
/*initializer*/ undefined);
const indexSignature = createIndexSignatureDeclaration(
/*decorators*/undefined,
/*modifiers*/ undefined,
[indexingParameter],
typeNode);
typeNode = typeNode || createKeywordTypeNode(SyntaxKind.AnyKeyword);
const indexSignatureChangeTracker = textChanges.ChangeTracker.fromCodeFixContext(context);
indexSignatureChangeTracker.insertNodeAfter(sourceFile, openBrace, indexSignature, { suffix: context.newLineCharacter });
const openBrace = getOpenBraceOfClassLike(classDeclaration, sourceFile);
return [{
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Add_declaration_for_missing_property_0), [token.getText()]),
changes: propertyChangeTracker.getChanges()
},
{
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Add_index_signature_for_missing_property_0), [token.getText()]),
changes: indexSignatureChangeTracker.getChanges()
}];
const property = createProperty(
/*decorators*/undefined,
/*modifiers*/ isStatic ? [createToken(SyntaxKind.StaticKeyword)] : undefined,
token.getText(sourceFile),
/*questionToken*/ undefined,
typeNode,
/*initializer*/ undefined);
const propertyChangeTracker = textChanges.ChangeTracker.fromCodeFixContext(context);
propertyChangeTracker.insertNodeAfter(sourceFile, openBrace, property, { suffix: context.newLineCharacter });
const actions = [{
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Add_declaration_for_missing_property_0), [token.getText()]),
changes: propertyChangeTracker.getChanges()
}];
if (!isStatic) {
const stringTypeNode = createKeywordTypeNode(SyntaxKind.StringKeyword);
const indexingParameter = createParameter(
/*decorators*/ undefined,
/*modifiers*/ undefined,
/*dotDotDotToken*/ undefined,
"x",
/*questionToken*/ undefined,
stringTypeNode,
/*initializer*/ undefined);
const indexSignature = createIndexSignatureDeclaration(
/*decorators*/undefined,
/*modifiers*/ undefined,
[indexingParameter],
typeNode);
const indexSignatureChangeTracker = textChanges.ChangeTracker.fromCodeFixContext(context);
indexSignatureChangeTracker.insertNodeAfter(sourceFile, openBrace, indexSignature, { suffix: context.newLineCharacter });
actions.push({
description: formatStringFromArgs(getLocaleSpecificMessage(Diagnostics.Add_index_signature_for_missing_property_0), [token.getText()]),
changes: indexSignatureChangeTracker.getChanges()
});
}
return actions;
}
}
}
+1
View File
@@ -7,4 +7,5 @@
/// <reference path="fixForgottenThisPropertyAccess.ts" />
/// <reference path='unusedIdentifierFixes.ts' />
/// <reference path='importFixes.ts' />
/// <reference path='disableJsDiagnostics.ts' />
/// <reference path='helpers.ts' />
+1
View File
@@ -482,6 +482,7 @@ namespace ts {
public moduleAugmentations: LiteralExpression[];
private namedDeclarations: Map<Declaration[]>;
public ambientModuleNames: string[];
public checkJsDirective: CheckJsDirective | undefined;
constructor(kind: SyntaxKind, pos: number, end: number) {
super(kind, pos, end);
+2 -1
View File
@@ -91,6 +91,7 @@
"codefixes/fixes.ts",
"codefixes/helpers.ts",
"codefixes/importFixes.ts",
"codefixes/unusedIdentifierFixes.ts"
"codefixes/unusedIdentifierFixes.ts",
"codefixes/disableJsDiagnostics.ts"
]
}
+7
View File
@@ -1380,6 +1380,13 @@ namespace ts {
};
}
export function getFirstNonSpaceCharacterPosition(text: string, position: number) {
while (isWhiteSpace(text.charCodeAt(position))) {
position += 1;
}
return position;
}
export function getOpenBrace(constructor: ConstructorDeclaration, sourceFile: SourceFile) {
// First token is the open curly, this is where we want to put the 'super' call.
return constructor.body.getFirstToken(sourceFile);
@@ -0,0 +1,9 @@
tests/cases/compiler/a.js(3,1): error TS2322: Type '0' is not assignable to type 'string'.
==== tests/cases/compiler/a.js (1 errors) ====
var x = "string";
x = 0;
~
!!! error TS2322: Type '0' is not assignable to type 'string'.
@@ -0,0 +1,10 @@
tests/cases/compiler/a.js(4,1): error TS2322: Type '0' is not assignable to type 'string'.
==== tests/cases/compiler/a.js (1 errors) ====
// @ts-check
var x = "string";
x = 0;
~
!!! error TS2322: Type '0' is not assignable to type 'string'.
@@ -0,0 +1,10 @@
tests/cases/compiler/a.js(4,1): error TS2322: Type '0' is not assignable to type 'string'.
==== tests/cases/compiler/a.js (1 errors) ====
// @ts-check
var x = "string";
x = 0;
~
!!! error TS2322: Type '0' is not assignable to type 'string'.
@@ -0,0 +1,10 @@
tests/cases/compiler/a.js(4,1): error TS2322: Type '0' is not assignable to type 'string'.
==== tests/cases/compiler/a.js (1 errors) ====
// @ts-check
var x = "string";
x = 0;
~
!!! error TS2322: Type '0' is not assignable to type 'string'.
@@ -0,0 +1,9 @@
=== tests/cases/compiler/a.js ===
// @ts-nocheck
var x = "string";
>x : Symbol(x, Decl(a.js, 2, 3))
x = 0;
>x : Symbol(x, Decl(a.js, 2, 3))
@@ -0,0 +1,12 @@
=== tests/cases/compiler/a.js ===
// @ts-nocheck
var x = "string";
>x : string
>"string" : "string"
x = 0;
>x = 0 : 0
>x : string
>0 : 0
@@ -0,0 +1,9 @@
error TS5052: Option 'checkJs' cannot be specified without specifying option 'allowJs'.
error TS6054: File 'tests/cases/compiler/a.js' has unsupported extension. The only supported extensions are '.ts', '.tsx', '.d.ts'.
!!! error TS5052: Option 'checkJs' cannot be specified without specifying option 'allowJs'.
!!! error TS6054: File 'tests/cases/compiler/a.js' has unsupported extension. The only supported extensions are '.ts', '.tsx', '.d.ts'.
==== tests/cases/compiler/a.js (0 errors) ====
var x;
@@ -0,0 +1,38 @@
=== tests/cases/compiler/a.js ===
var x = 0;
>x : Symbol(x, Decl(a.js, 1, 3))
/// @ts-ignore
x();
>x : Symbol(x, Decl(a.js, 1, 3))
/// @ts-ignore
x();
>x : Symbol(x, Decl(a.js, 1, 3))
/// @ts-ignore
x(
>x : Symbol(x, Decl(a.js, 1, 3))
2,
3);
// @ts-ignore
// come comment
// some other comment
// @anohter
x();
>x : Symbol(x, Decl(a.js, 1, 3))
// @ts-ignore: no call signature
x();
>x : Symbol(x, Decl(a.js, 1, 3))
@@ -0,0 +1,47 @@
=== tests/cases/compiler/a.js ===
var x = 0;
>x : number
>0 : 0
/// @ts-ignore
x();
>x() : any
>x : number
/// @ts-ignore
x();
>x() : any
>x : number
/// @ts-ignore
x(
>x( 2, 3) : any
>x : number
2,
>2 : 2
3);
>3 : 3
// @ts-ignore
// come comment
// some other comment
// @anohter
x();
>x() : any
>x : number
// @ts-ignore: no call signature
x();
>x() : any
>x : number
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
"jsx": "react", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"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: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"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: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
@@ -5,6 +5,7 @@
"module": "commonjs", /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd' or 'es2015'. */
// "lib": [], /* Specify library files to be included in the compilation: */
// "allowJs": true, /* Allow javascript files to be compiled. */
// "checkJs": true, /* Report errors in .js files. */
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */
// "declaration": true, /* Generates corresponding '.d.ts' file. */
// "sourceMap": true, /* Generates corresponding '.map' file. */
+7
View File
@@ -0,0 +1,7 @@
// @allowJs: true
// @checkJs: true
// @noEmit: true
// @fileName: a.js
var x = "string";
x = 0;
+8
View File
@@ -0,0 +1,8 @@
// @allowJs: true
// @checkJs: false
// @noEmit: true
// @fileName: a.js
// @ts-check
var x = "string";
x = 0;
+7
View File
@@ -0,0 +1,7 @@
// @allowJs: true
// @noEmit: true
// @fileName: a.js
// @ts-check
var x = "string";
x = 0;
+8
View File
@@ -0,0 +1,8 @@
// @allowJs: true
// @checkJs: false
// @noEmit: true
// @fileName: a.js
// @ts-check
var x = "string";
x = 0;
+8
View File
@@ -0,0 +1,8 @@
// @allowJs: true
// @checkJs: true
// @noEmit: true
// @fileName: a.js
// @ts-nocheck
var x = "string";
x = 0;
+6
View File
@@ -0,0 +1,6 @@
// @allowJs: false
// @checkJs: true
// @noEmit: true
// @fileName: a.js
var x;
@@ -0,0 +1,33 @@
// @allowJs: true
// @checkJs: true
// @noEmit: true
// @fileName: a.js
var x = 0;
/// @ts-ignore
x();
/// @ts-ignore
x();
/// @ts-ignore
x(
2,
3);
// @ts-ignore
// come comment
// some other comment
// @anohter
x();
// @ts-ignore: no call signature
x();
@@ -0,0 +1,14 @@
/// <reference path='fourslash.ts' />
////[|class C {
//// method() {
//// this.foo = 10;
//// }
////}|]
verify.rangeAfterCodeFix(`class C {
foo: number;
method() {
this.foo = 10;
}
}`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,14 @@
/// <reference path='fourslash.ts' />
////[|class C {
//// method() {
//// this.foo = 10;
//// }
////}|]
verify.rangeAfterCodeFix(`class C {
[x:string]: number;
method() {
this.foo = 10;
}
}`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 1);
@@ -0,0 +1,14 @@
/// <reference path='fourslash.ts' />
////[|class C {
//// static method() {
//// this.foo = 10;
//// }
////}|]
verify.rangeAfterCodeFix(`class C {
static foo: number;
static method() {
this.foo = 10;
}
}`);
@@ -0,0 +1,22 @@
/// <reference path='fourslash.ts' />
// @checkJs: true
// @allowJs: true
// @Filename: a.js
////[|class C {
//// constructor() {
//// }
//// method() {
//// this.foo === 10;
//// }
////}|]
verify.rangeAfterCodeFix(`class C {
constructor() {
this.foo = undefined;
}
method() {
this.foo === 10;
}
}`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,19 @@
/// <reference path='fourslash.ts' />
// @checkJs: true
// @allowJs: true
// @Filename: a.js
////[|class C {
//// static method() {
//// ()=>{ this.foo === 10 };
//// }
////}
////|]
verify.rangeAfterCodeFix(`class C {
static method() {
()=>{ this.foo === 10 };
}
}
C.foo = undefined;`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,18 @@
/// <reference path='fourslash.ts' />
// @checkJs: true
// @allowJs: true
// @Filename: a.js
////[|class C {
//// constructor() {
//// }
//// prop = ()=>{ this.foo === 10 };
////}|]
verify.rangeAfterCodeFix(`class C {
constructor() {
this.foo = undefined;
}
prop = ()=>{ this.foo === 10 };
}`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,15 @@
/// <reference path='fourslash.ts' />
// @checkJs: true
// @allowJs: true
// @Filename: a.js
////[|class C {
//// static p = ()=>{ this.foo === 10 };
////}
////|]
verify.rangeAfterCodeFix(`class C {
static p = ()=>{ this.foo === 10 };
}
C.foo = undefined;`, /*includeWhiteSpace*/false, /*errorCode*/ undefined, /*index*/ 2);
@@ -0,0 +1,11 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @Filename: a.js
////[|// @ts-check|]
////var x = "";
////x = 1;
verify.rangeAfterCodeFix("// @ts-nocheck", /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 1);
@@ -0,0 +1,15 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////[|var x = "";
////x = 1;|]
// Disable checking for the whole file
verify.rangeAfterCodeFix(`// @ts-nocheck
var x = "";
x = 1;`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 1);
@@ -0,0 +1,14 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////[|var x = "";
////x = 1;|]
// Disable checking for next line
verify.rangeAfterCodeFix(`var x = "";
// @ts-ignore
x = 1;`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,18 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////var x = "";
////
////[|"test \
////"; x = 1;|]
// Disable checking for next line
verify.rangeAfterCodeFix(`"test \\
";
// @ts-ignore
x = 1;`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,17 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////var x = "";
////
////[|/** comment */
////x = 1;|]
// Disable checking for next line
verify.rangeAfterCodeFix(`/** comment */
// @ts-ignore
x = 1;`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,17 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////var x = 0;
////
////function f(_a) {
//// [|f(x());|]
////}
// Disable checking for next line
verify.rangeAfterCodeFix(`// @ts-ignore
f(x());`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,17 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////var x = 0;
////
////function f(_a) {
//// [|x();|]
////}
// Disable checking for next line
verify.rangeAfterCodeFix(`// @ts-ignore
x();`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
@@ -0,0 +1,19 @@
/// <reference path='fourslash.ts' />
// @allowjs: true
// @noEmit: true
// @checkJs: true
// @Filename: a.js
////var x = 0;
////
////function f(_a) {
//// /** comment for f */
//// [|f(x());|]
////}
// Disable checking for next line
verify.rangeAfterCodeFix(`f(
// @ts-ignore
x());`, /*includeWhiteSpace*/ false, /*errorCode*/ undefined, /*index*/ 0);
+1
View File
@@ -296,6 +296,7 @@ declare namespace FourSlashInterface {
printCurrentQuickInfo(): void;
printCurrentSignatureHelp(): void;
printCompletionListMembers(): void;
printAvailableCodeFixes(): void;
printBreakpointLocation(pos: number): void;
printBreakpointAtCurrentLocation(): void;
printNameOrDottedNameSpans(pos: number): void;