diff --git a/src/util.js b/src/util.js index ae727036..91c6e99e 100644 --- a/src/util.js +++ b/src/util.js @@ -119,14 +119,20 @@ util.getLast = function(arr) { }; function skipNewLineForward(text, index) { - if (text.charAt(index) === "\n") { - return index + 1; + // What the "end" location points to is not consistent in parsers. + // For some statement/expressions, it's the character immediately + // afterward. For others, it's the last character in it. We need to + // scan until we hit a newline in order to skip it. + while(index < text.length) { + if (text.charAt(index) === "\n") { + return index + 1; + } + if (text.charAt(index) === "\r" && text.charAt(index + 1) === "\n") { + return index + 2; + } + index++; } - if (text.charAt(index) === "\r" && text.charAt(index + 1) === "\n") { - return index + 2; - } - // Note: this is incorrect, but makes the current tests pass for now. - return index + 1; + return index; } function _findNewline(text, index, backwards) { diff --git a/tests/annot/__snapshots__/jsfmt.spec.js.snap b/tests/annot/__snapshots__/jsfmt.spec.js.snap index 587e49d2..87d526d8 100644 --- a/tests/annot/__snapshots__/jsfmt.spec.js.snap +++ b/tests/annot/__snapshots__/jsfmt.spec.js.snap @@ -148,12 +148,14 @@ function foo() { } ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ let myClassInstance: MyClass = null; + // forward ref ok, null ~> class error function bar(): MyClass { return null; // forward ref ok, null ~> class error } class MyClass {} + // looked up above function foo() { let myClassInstance: MyClass = mk(); diff --git a/tests/arith/__snapshots__/jsfmt.spec.js.snap b/tests/arith/__snapshots__/jsfmt.spec.js.snap index 37a6a692..4505203d 100644 --- a/tests/arith/__snapshots__/jsfmt.spec.js.snap +++ b/tests/arith/__snapshots__/jsfmt.spec.js.snap @@ -139,6 +139,7 @@ function bar5(x: number, y?: ?number) { num(null + null); // === 0 num(undefined + undefined); + // === NaN num(null + 1); // === 1 @@ -147,6 +148,7 @@ num(1 + null); num(undefined + 1); // === NaN num(1 + undefined); + // === NaN num(null + true); // === 1 @@ -155,6 +157,7 @@ num(true + null); num(undefined + true); // === NaN num(true + undefined); + // === NaN str(\"foo\" + true); // error @@ -167,6 +170,7 @@ str(null + \"foo\"); str(\"foo\" + undefined); // error str(undefined + \"foo\"); + // error let tests = [ function(x: mixed, y: mixed) { @@ -200,6 +204,7 @@ let tests = [ (x + y: string); // ok (y + x: string); + // ok (x + z: empty); // error, string ~> empty @@ -229,6 +234,7 @@ x **= 4; let y: string = \"123\"; y **= 2; + // error 1 + 2 ** 3 + 4; 2 ** 2; @@ -348,11 +354,13 @@ let tests = [ \"foo\" < { foo: 1 }; // error ({ foo: 1 }) < \"foo\"; + // error var x = (null: ?number); 1 < x; // 2 errors: null !~> number; undefined !~> number x < 1; + // 2 errors: null !~> number; undefined !~> number null < null; // error diff --git a/tests/arraylib/__snapshots__/jsfmt.spec.js.snap b/tests/arraylib/__snapshots__/jsfmt.spec.js.snap index 4530854c..85c1c798 100644 --- a/tests/arraylib/__snapshots__/jsfmt.spec.js.snap +++ b/tests/arraylib/__snapshots__/jsfmt.spec.js.snap @@ -64,6 +64,7 @@ function foo(x: string) { var a = [ 0 ]; var b = a.map(function(x) { foo(x); + return \"\" + x; }); @@ -84,6 +85,7 @@ var k: Array = h.concat(h); var l: Array = h.concat(1, 2, 3); var m: Array = h.concat(\"a\", \"b\", \"c\"); var n: Array = h.concat(\"a\", \"b\", \"c\"); + // Error function reduce_test() { /* Adapted from the following source: diff --git a/tests/arrows/__snapshots__/jsfmt.spec.js.snap b/tests/arrows/__snapshots__/jsfmt.spec.js.snap index 9e447683..4858de59 100644 --- a/tests/arrows/__snapshots__/jsfmt.spec.js.snap +++ b/tests/arrows/__snapshots__/jsfmt.spec.js.snap @@ -18,6 +18,7 @@ var ident = (x: T): T => x; var add = (x: number, y: number): number => x + y; var bad = (x: number): string => x; + // Error! var ident = (x: T): T => x; (ident(1): number); diff --git a/tests/async/__snapshots__/jsfmt.spec.js.snap b/tests/async/__snapshots__/jsfmt.spec.js.snap index 463e3906..ab791989 100644 --- a/tests/async/__snapshots__/jsfmt.spec.js.snap +++ b/tests/async/__snapshots__/jsfmt.spec.js.snap @@ -352,6 +352,7 @@ function test2() { } var voidoid2: () => Promise = voidoid1; + // ok var voidoid3: () => void = voidoid1; // error, void != Promise } diff --git a/tests/binding/__snapshots__/jsfmt.spec.js.snap b/tests/binding/__snapshots__/jsfmt.spec.js.snap index effea2a9..cace3938 100644 --- a/tests/binding/__snapshots__/jsfmt.spec.js.snap +++ b/tests/binding/__snapshots__/jsfmt.spec.js.snap @@ -49,6 +49,7 @@ const [ bar ] = [ \"bar\" ]; (foo: number); // error: string ~> number (bar: number); + // error: string ~> number declare var bazzes: { baz: string }[]; for (const { baz } of bazzes) { @@ -412,7 +413,6 @@ function var_var() { function function_toplevel() { function a() { } - function a() { } } @@ -421,7 +421,6 @@ function function_block() { { function a() { } - function a() { } } @@ -889,24 +888,29 @@ function f5() { // phasing of AST traversal, and will be fixed. // var x: C; + // ok var y = new C(); + // error: let ref before decl from value position class C {} var z: C = new C(); + // ok // --- vars --- // it\'s possible to annotate a var with a non-maybe type, // but leave it uninitialized until later (as long as it\'s // initialized before use) var a: number; + // not an error per se - only if used before init function f(n: number) { return n; } f(a); + // error: undefined ~/> number a = 10; diff --git a/tests/bom/__snapshots__/jsfmt.spec.js.snap b/tests/bom/__snapshots__/jsfmt.spec.js.snap index 7754aeac..c2269010 100644 --- a/tests/bom/__snapshots__/jsfmt.spec.js.snap +++ b/tests/bom/__snapshots__/jsfmt.spec.js.snap @@ -77,9 +77,11 @@ new FormData(\"\"); new FormData(document.createElement(\"input\")); // incorrect new FormData(document.createElement(\"form\")); + // correct // has const b: boolean = a.has(\"foo\"); + // correct // get const c: ?(string | File) = a.get(\"foo\"); @@ -91,6 +93,7 @@ const e: Blob = a.get(\"foo\"); const f: ?(string | File | Blob) = a.get(\"foo\"); // incorrect a.get(2); + // incorrect // getAll const a1: Array = a.getAll(\"foo\"); @@ -100,6 +103,7 @@ const a2: Array = a.getAll(\"foo\"); const a3: Array = a.getAll(\"foo\"); // incorrect a.getAll(23); + // incorrect // set a.set(\"foo\", \"bar\"); @@ -121,6 +125,7 @@ a.set(\"bar\", new Blob()); a.set(\"bar\", new Blob(), \"x\"); // correct a.set(\"bar\", new Blob(), 2); + // incorrect // append a.append(\"foo\", \"bar\"); @@ -144,11 +149,13 @@ a.append(\"bar\", new Blob()); a.append(\"bar\", new Blob(), \"x\"); // correct a.append(\"bar\", new Blob(), 2); + // incorrect // delete a.delete(\"xx\"); // correct a.delete(3); + // incorrect // keys for (let x: string of a.keys()) { @@ -156,6 +163,7 @@ for (let x: string of a.keys()) { // correct for (let x: number of a.keys()) { } + // incorrect // values for (let x: string | File of a.values()) { @@ -163,6 +171,7 @@ for (let x: string | File of a.values()) { // correct for (let x: string | File | Blob of a.values()) { } + // incorrect // entries for (let [ x, y ]: [string, string | File] of a.entries()) { @@ -235,6 +244,7 @@ new MutationObserver(42); // incorrect new MutationObserver((n: number) => { }); + // incorrect // observe const div = document.createElement(\"div\"); @@ -253,9 +263,11 @@ o.observe(div, {}); o.observe(div, { subtree: true }); // incorrect o.observe(div, { attributes: true, attributeFilter: true }); + // incorrect // takeRecords o.takeRecords(); + // correct // disconnect o.disconnect(); // correct diff --git a/tests/builtins/__snapshots__/jsfmt.spec.js.snap b/tests/builtins/__snapshots__/jsfmt.spec.js.snap index 75b39770..de299bb3 100644 --- a/tests/builtins/__snapshots__/jsfmt.spec.js.snap +++ b/tests/builtins/__snapshots__/jsfmt.spec.js.snap @@ -22,6 +22,7 @@ var b = a.map(function(x) { return 0; }); var c: string = b[0]; + // error: number !~> string var array = []; function f() { diff --git a/tests/call_properties/__snapshots__/jsfmt.spec.js.snap b/tests/call_properties/__snapshots__/jsfmt.spec.js.snap index 24509cde..06143a50 100644 --- a/tests/call_properties/__snapshots__/jsfmt.spec.js.snap +++ b/tests/call_properties/__snapshots__/jsfmt.spec.js.snap @@ -115,6 +115,7 @@ var f: { (): mixed } = function(): string { // return type var g: { (x: string): void } = function(x: mixed) { }; + // param type // A function can be an object var y: {} = function(x: number): string { @@ -323,6 +324,7 @@ var f: { (): mixed } = () => \"hi\"; var g: { (x: Date): void } = x => { x * 2; }; + // param type (date < number) // A function can be an object var y: {} = x => \"hi\"; diff --git a/tests/callable/__snapshots__/jsfmt.spec.js.snap b/tests/callable/__snapshots__/jsfmt.spec.js.snap index f386a880..21a55d9f 100644 --- a/tests/callable/__snapshots__/jsfmt.spec.js.snap +++ b/tests/callable/__snapshots__/jsfmt.spec.js.snap @@ -50,12 +50,14 @@ foo(Boolean); var dict: { [k: string]: any } = {}; dict(); + // error, callable signature not found interface ICall { (x: string): void } declare var icall: ICall; icall(0); // error, number ~> string icall.call(null, 0); + // error, number ~> string type Callable = { (x: string): void }; diff --git a/tests/class_statics/__snapshots__/jsfmt.spec.js.snap b/tests/class_statics/__snapshots__/jsfmt.spec.js.snap index 8cf1ec6f..2d551972 100644 --- a/tests/class_statics/__snapshots__/jsfmt.spec.js.snap +++ b/tests/class_statics/__snapshots__/jsfmt.spec.js.snap @@ -71,6 +71,7 @@ class A { } A.qux = function(x: string) { }; + // error? class B extends A { static x: string; @@ -112,6 +113,7 @@ class C { class D extends C { static main() { D.foo(0); + // error? D.bar(0); } diff --git a/tests/classes/__snapshots__/jsfmt.spec.js.snap b/tests/classes/__snapshots__/jsfmt.spec.js.snap index 43863824..4644dbbd 100644 --- a/tests/classes/__snapshots__/jsfmt.spec.js.snap +++ b/tests/classes/__snapshots__/jsfmt.spec.js.snap @@ -30,6 +30,7 @@ class B extends A {} let b = new B(); (b.foo: number); + // error, number !~> function module.exports = B; " @@ -56,6 +57,7 @@ class C extends B { let c = new C(); (c.foo: number); + // error, number !~> function module.exports = C; " @@ -135,11 +137,13 @@ x.b; x.c; // ok x.d; + // error, TestClass has no d var y: Foo = x; y.b; // error, doesn\'t exist in TestClass y.d; + // ok, it\'s optional class Test2Superclass { a: number; @@ -197,14 +201,17 @@ var Bar = class Foo { var bar1: Bar = new Bar(); // OK var bar2: Bar = Bar.factory(); + // OK // NB: Don\'t write expected errors using Foo to avoid error collapse hiding an // unexpected failure in the above code. var B = class Baz {}; var b = new Baz(); + // error: Baz is not a runtime binding in this scope var C = class Qux {}; var c: Qux = new C(); + // error: Qux is not a type in this scope // OK: anon classes create no binding, but can be bound manually var Anon = class {}; @@ -263,6 +270,7 @@ C.p = \"hi\"; (C: { p: string }); // ok (C: { p: number }); + // errors, string ~> number & vice versa (unify) declare var o: { p: number }; (o: Class); // error, object type incompatible with class type diff --git a/tests/closure/__snapshots__/jsfmt.spec.js.snap b/tests/closure/__snapshots__/jsfmt.spec.js.snap index 740bb6e7..65dd6fce 100644 --- a/tests/closure/__snapshots__/jsfmt.spec.js.snap +++ b/tests/closure/__snapshots__/jsfmt.spec.js.snap @@ -100,11 +100,14 @@ function global_g() { global_f(); takes_string(global_x); + // ok global_g(); takes_string(global_x); + // error global_x = 42; + // shouldn\'t pollute linear refinement // local write from function // @@ -119,9 +122,11 @@ function local_func() { local_f(); takes_string(local_x); + // ok local_g(); takes_string(local_x); + // error local_x = 42; // shouldn\'t pollute linear refinement } @@ -140,11 +145,14 @@ var global_o = { global_o.f(); takes_string(global_y); + // ok global_o.g(); takes_string(global_y); + // error global_y = 42; + // shouldn\'t pollute linear refinement // local write from method // @@ -161,9 +169,11 @@ function local_meth() { local_o.f(); takes_string(local_y); + // ok local_o.g(); takes_string(local_y); + // error local_y = 42; // shouldn\'t pollute linear refinement } diff --git a/tests/computed_props/__snapshots__/jsfmt.spec.js.snap b/tests/computed_props/__snapshots__/jsfmt.spec.js.snap index ece1edb2..518241ff 100644 --- a/tests/computed_props/__snapshots__/jsfmt.spec.js.snap +++ b/tests/computed_props/__snapshots__/jsfmt.spec.js.snap @@ -34,8 +34,10 @@ var ColorIdToNumber = { }; (ColorIdToNumber[ColorId.RED]: \"ffffff\"); + // oops ColorIdToNumber.XXX; + // oops module.exports = { ColorId, ColorNumber }; " @@ -61,6 +63,7 @@ var ColorIdToNumber = { }; (ColorIdToNumber[ColorId.GREEN]: \"ffffff\"); + // oops module.exports = ColorIdToNumber; " @@ -124,6 +127,7 @@ var obj = { } }; var x: string = obj[\"m\"](); + // error, number ~> string var arr = [ function() { diff --git a/tests/config_module_name_rewrite_node/__snapshots__/jsfmt.spec.js.snap b/tests/config_module_name_rewrite_node/__snapshots__/jsfmt.spec.js.snap index 3994fc97..fb201ffb 100644 --- a/tests/config_module_name_rewrite_node/__snapshots__/jsfmt.spec.js.snap +++ b/tests/config_module_name_rewrite_node/__snapshots__/jsfmt.spec.js.snap @@ -34,6 +34,7 @@ var a_2: string = m1.numVal; import { numVal } from \"./1DoesntExist\"; var a_3: number = numVal; var a_4: string = numVal; + // Error: number ~> string // This tests that, for node, the first name mapping that both matches *and* // results in a valid module filename is picked. @@ -44,6 +45,7 @@ var b_2: string = m2.numVal; import { numVal as numVal2 } from \"./3DoesntExist\"; var b_3: number = numVal2; var b_4: string = numVal2; + // Error: number ~> string // node_modules/Exists/index.js var m3 = require(\"4DoesntExist\"); diff --git a/tests/core_tests/__snapshots__/jsfmt.spec.js.snap b/tests/core_tests/__snapshots__/jsfmt.spec.js.snap index 211b66f7..0f7a856b 100644 --- a/tests/core_tests/__snapshots__/jsfmt.spec.js.snap +++ b/tests/core_tests/__snapshots__/jsfmt.spec.js.snap @@ -274,6 +274,7 @@ ws.delete(dict); let ws2 = new WeakSet([ obj, dict ]); let ws3 = new WeakSet([ 1, 2, 3 ]); + // error, must be objects function* generator(): Iterable<{ foo: string }> { while (true) { diff --git a/tests/covariance/__snapshots__/jsfmt.spec.js.snap b/tests/covariance/__snapshots__/jsfmt.spec.js.snap index 901c744e..1862bb4b 100644 --- a/tests/covariance/__snapshots__/jsfmt.spec.js.snap +++ b/tests/covariance/__snapshots__/jsfmt.spec.js.snap @@ -53,6 +53,7 @@ type CovArrayVerbose = Array; var b: CovArrayVerbose = []; var y: CovArrayVerbose = b; y[0] = \"\"; + // error class NVerbose { x: CovArrayVerbose; diff --git a/tests/declaration_files_incremental_haste/__snapshots__/jsfmt.spec.js.snap b/tests/declaration_files_incremental_haste/__snapshots__/jsfmt.spec.js.snap index b695f6a9..f7d57ce5 100644 --- a/tests/declaration_files_incremental_haste/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declaration_files_incremental_haste/__snapshots__/jsfmt.spec.js.snap @@ -91,9 +91,11 @@ var ExplicitDifferentName = require(\'ExplicitProvidesModuleDifferentName\'); var Implicit = require(\"ImplicitProvidesModule\"); (Implicit.fun(): boolean); + // Error: Either Implementation ~> boolean or Declaration ~> boolean var ExplicitSameName = require(\"ExplicitProvidesModuleSameName\"); (ExplicitSameName.fun(): boolean); + // Error: Either Implementation ~> boolean or Declaration ~> boolean var ExplicitDifferentName = require(\"ExplicitProvidesModuleDifferentName\"); (ExplicitDifferentName.fun(): boolean); // Error: Either Implementation ~> boolean or Declaration ~> boolean diff --git a/tests/declaration_files_incremental_node/__snapshots__/jsfmt.spec.js.snap b/tests/declaration_files_incremental_node/__snapshots__/jsfmt.spec.js.snap index 62dd9584..783a4acb 100644 --- a/tests/declaration_files_incremental_node/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declaration_files_incremental_node/__snapshots__/jsfmt.spec.js.snap @@ -57,39 +57,50 @@ var F = require(\'package_with_dir_main\'); // This will require ./node_modules/B.js.flow var B1 = require(\"B\"); (B1.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean // This will require ./node_modules/B.js.flow var B2 = require(\"B.js\"); (B2.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var C = require(\"package_with_full_main\"); (C.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var D = require(\"package_with_partial_main\"); (D.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var E = require(\"package_with_no_package_json\"); (E.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var F = require(\"package_with_dir_main\"); (F.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean // This will require ./node_modules/B.js.flow var B1 = require(\"B\"); (B1.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean // This will require ./node_modules/B.js.flow var B2 = require(\"B.js\"); (B2.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var C = require(\"package_with_full_main\"); (C.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var D = require(\"package_with_partial_main\"); (D.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var E = require(\"package_with_no_package_json\"); (E.fun(): boolean); + // Error either Implementation ~> boolean or Declaration ~> boolean var F = require(\"package_with_dir_main\"); (F.fun(): boolean); // Error either Implementation ~> boolean or Declaration ~> boolean diff --git a/tests/declaration_files_node/__snapshots__/jsfmt.spec.js.snap b/tests/declaration_files_node/__snapshots__/jsfmt.spec.js.snap index 68d46b79..05fb2358 100644 --- a/tests/declaration_files_node/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declaration_files_node/__snapshots__/jsfmt.spec.js.snap @@ -46,19 +46,24 @@ var F = require(\'package_with_dir_main\'); // This will require ./node_modules/B.js.flow var B1 = require(\"B\"); (B1.fun(): string); + // Error number ~> string // This will require ./node_modules/B.js.flow var B2 = require(\"B.js\"); (B2.fun(): string); + // Error number ~> string var C = require(\"package_with_full_main\"); (C.fun(): string); + // Error number ~> string var D = require(\"package_with_partial_main\"); (D.fun(): string); + // Error number ~> string var E = require(\"package_with_no_package_json\"); (E.fun(): string); + // Error number ~> string var F = require(\"package_with_dir_main\"); (F.fun(): string); // Error number ~> string @@ -85,10 +90,12 @@ var CJS = require(\'./CJS.js\'); // This will require ./A.js.flow var A1 = require(\"./A\"); (A1.fun(): string); + // Error number ~> string // This will require ./A.js.flow var A2 = require(\"./A.js\"); (A2.fun(): string); + // Error number ~> string var CJS = require(\"./CJS.js\"); (CJS: string); diff --git a/tests/declare_export/__snapshots__/jsfmt.spec.js.snap b/tests/declare_export/__snapshots__/jsfmt.spec.js.snap index fa2f9202..cd783ecf 100644 --- a/tests/declare_export/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declare_export/__snapshots__/jsfmt.spec.js.snap @@ -204,7 +204,6 @@ declare export default class Foo { givesANum(): number; }; */ declare export default class Foo { givesANum(): number } - " `; @@ -890,36 +889,44 @@ var at4: string = numberValue9; // Error: number ~> string import * as DefaultA from \"A\"; var a1: number = DefaultA.numberValue1; var a2: string = DefaultA.numberValue1; + // Error: number ~> string // File path import * as DefaultB from \"./B\"; var b1: number = DefaultB.numberValue; var b2: string = DefaultB.numberValue; + // Error: number ~> string // C.js exists, but not as a providesModule import DefaultC from \"C\"; + // Error: No such module // @providesModule D exists, but not as a filename import DefaultD from \"./D\"; + // Error: No such module // ================================================ // // == CommonJS Clobbering Literal Exports -> ES6 == // // ================================================ // import { doesntExist1 } from \"CommonJS_Clobbering_Lit\"; + // Error: Not an exported binding import { numberValue1 } from \"CommonJS_Clobbering_Lit\"; var c1: number = numberValue1; var c2: string = numberValue1; + // Error: number ~> string import { numberValue2 as numVal1 } from \"CommonJS_Clobbering_Lit\"; var d1: number = numVal1; var d2: string = numVal1; + // Error: number ~> string import CJS_Clobb_Lit from \"CommonJS_Clobbering_Lit\"; var e1: number = CJS_Clobb_Lit.numberValue3; var e2: string = CJS_Clobb_Lit.numberValue3; // Error: number ~> string CJS_Clobb_Lit.doesntExist; + // Error: doesntExist isn\'t a property import * as CJS_Clobb_Lit_NS from \"CommonJS_Clobbering_Lit\"; var f1: number = CJS_Clobb_Lit_NS.numberValue4; @@ -929,17 +936,20 @@ CJS_Clobb_Lit_NS.default.default; var f3: string = CJS_Clobb_Lit_NS.numberValue4; // Error: number ~> string var f4: string = CJS_Clobb_Lit_NS.default.numberValue5; + // Error: number ~> string // ============================================== // // == CommonJS Clobbering Class Exports -> ES6 == // // ============================================== // import { doesntExist2 } from \"CommonJS_Clobbering_Class\"; + // Error: Not an exported binding // The following import should error because class statics are not turned into // named exports for now. This avoids complexities with polymorphic static // members (where the polymophism is defined on the class itself rather than the // method). import { staticNumber1, baseProp, childProp } from \"CommonJS_Clobbering_Class\"; + // Error import CJS_Clobb_Class from \"CommonJS_Clobbering_Class\"; new CJS_Clobb_Class(); @@ -950,6 +960,7 @@ var h2: string = CJS_Clobb_Class.staticNumber2(); // Error: number ~> string var h3: number = new CJS_Clobb_Class().instNumber1(); var h4: string = new CJS_Clobb_Class().instNumber1(); + // Error: number ~> string import * as CJS_Clobb_Class_NS from \"CommonJS_Clobbering_Class\"; new CJS_Clobb_Class_NS(); @@ -958,65 +969,79 @@ var i1: number = CJS_Clobb_Class_NS.staticNumber3(); // Error: Class statics not copied to Namespace object var i2: number = new CJS_Clobb_Class_NS.default().instNumber2(); var i3: string = new CJS_Clobb_Class_NS.default().instNumber2(); + // Error: number ~> string // =================================== // // == CommonJS Named Exports -> ES6 == // // =================================== // import { doesntExist3 } from \"CommonJS_Named\"; + // Error: Not an exported binding import { numberValue2 } from \"CommonJS_Named\"; var j1: number = numberValue2; var j2: string = numberValue2; + // Error: number ~> string import { numberValue3 as numVal3 } from \"CommonJS_Named\"; var k1: number = numVal3; var k2: string = numVal3; + // Error: number ~> string import * as CJS_Named from \"CommonJS_Named\"; var l1: number = CJS_Named.numberValue1; var l2: string = CJS_Named.numberValue1; // Error: number ~> string CJS_Named.doesntExist; + // Error: doesntExist isn\'t a property import * as CJS_Named_NS from \"CommonJS_Named\"; var m1: number = CJS_Named_NS.numberValue4; var m2: string = CJS_Named_NS.default.numberValue4; // Error: CommonJS_Named has no default export var m3: string = CJS_Named_NS.numberValue4; + // Error: number ~> string ////////////////////////////// // == ES6 Default -> ES6 == // ////////////////////////////// import { doesntExist4 } from \"ES6_Default_AnonFunction1\"; + // Error: Not an exported binding import ES6_Def_AnonFunc1 from \"ES6_Default_AnonFunction1\"; var n1: number = ES6_Def_AnonFunc1(); var n2: string = ES6_Def_AnonFunc1(); + // Error: number ~> string import ES6_Def_NamedFunc1 from \"ES6_Default_NamedFunction1\"; var o1: number = ES6_Def_NamedFunc1(); var o2: string = ES6_Def_NamedFunc1(); + // Error: number ~> string import ES6_Def_NamedClass1 from \"ES6_Default_NamedClass1\"; var q1: number = new ES6_Def_NamedClass1().givesANum(); var q2: string = new ES6_Def_NamedClass1().givesANum(); + // Error: number ~> string //////////////////////////// // == ES6 Named -> ES6 == // //////////////////////////// import doesntExist5 from \"ES6_Named1\"; + // Error: Not an exported binding import { specifierNumber1 as specifierNumber1_1 } from \"ES6_Named1\"; var r1: number = specifierNumber1_1; var r2: string = specifierNumber1_1; + // Error: number ~> string import { specifierNumber2Renamed } from \"ES6_Named1\"; var s1: number = specifierNumber2Renamed; var s2: string = specifierNumber2Renamed; + // Error: number ~> string import { specifierNumber3 as specifierNumber3Renamed } from \"ES6_Named1\"; var t1: number = specifierNumber3Renamed; var t2: string = specifierNumber3Renamed; + // Error: number ~> string import { groupedSpecifierNumber1, groupedSpecifierNumber2 } from \"ES6_Named1\"; var u1: number = groupedSpecifierNumber1; @@ -1024,14 +1049,17 @@ var u2: number = groupedSpecifierNumber2; var u3: string = groupedSpecifierNumber1; // Error: number ~> string var u4: string = groupedSpecifierNumber2; + // Error: number ~> string import { givesANumber } from \"ES6_Named1\"; var v1: number = givesANumber(); var v2: string = givesANumber(); + // Error: number ~> string import { NumberGenerator } from \"ES6_Named1\"; var w1: number = new NumberGenerator().givesANumber(); var w2: string = new NumberGenerator().givesANumber(); + // Error: number ~> string import { varDeclNumber1, varDeclNumber2 } from \"ES6_Named1\"; var x1: number = varDeclNumber1; @@ -1039,35 +1067,43 @@ var x2: number = varDeclNumber2; var x3: string = varDeclNumber1; // Error: number ~> string var x4: string = varDeclNumber2; + // Error: number ~> string import { numberValue1 as numberValue4 } from \"ES6_ExportFrom_Intermediary1\"; var aa1: number = numberValue4; var aa2: string = numberValue4; + // Error: number ~> string import { numberValue2_renamed } from \"ES6_ExportFrom_Intermediary1\"; var ab1: number = numberValue2_renamed; var ab2: string = numberValue2_renamed; + // Error: number ~> string import { numberValue1 as numberValue5 } from \"ES6_ExportAllFrom_Intermediary1\"; var ac1: number = numberValue5; var ac2: string = numberValue5; + // Error: number ~> string /////////////////////////////////// // == ES6 Default -> CommonJS == // /////////////////////////////////// require(\"ES6_Default_AnonFunction2\").doesntExist; + // Error: \'doesntExist\' isn\'t an export var ES6_Def_AnonFunc2 = require(\"ES6_Default_AnonFunction2\").default; var ad1: number = ES6_Def_AnonFunc2(); var ad2: string = ES6_Def_AnonFunc2(); + // Error: number ~> string var ES6_Def_NamedFunc2 = require(\"ES6_Default_NamedFunction2\").default; var ae1: number = ES6_Def_NamedFunc2(); var ae2: string = ES6_Def_NamedFunc2(); + // Error: number ~> string var ES6_Def_NamedClass2 = require(\"ES6_Default_NamedClass2\").default; var ag1: number = new ES6_Def_NamedClass2().givesANum(); var ag2: string = new ES6_Def_NamedClass2().givesANum(); + // Error: number ~> string ///////////////////////////////// // == ES6 Named -> CommonJS == // @@ -1075,10 +1111,12 @@ var ag2: string = new ES6_Def_NamedClass2().givesANum(); var specifierNumber4 = require(\"ES6_Named2\").specifierNumber4; var ah1: number = specifierNumber4; var ah2: string = specifierNumber4; + // Error: number ~> string var specifierNumber5Renamed = require(\"ES6_Named2\").specifierNumber5Renamed; var ai1: number = specifierNumber5Renamed; var ai2: string = specifierNumber5Renamed; + // Error: number ~> string var groupedSpecifierNumber3 = require(\"ES6_Named2\").groupedSpecifierNumber3; var groupedSpecifierNumber4 = require(\"ES6_Named2\").groupedSpecifierNumber4; @@ -1087,14 +1125,17 @@ var aj2: number = groupedSpecifierNumber4; var aj3: string = groupedSpecifierNumber3; // Error: number ~> string var aj4: string = groupedSpecifierNumber4; + // Error: number ~> string var givesANumber2 = require(\"ES6_Named2\").givesANumber2; var ak1: number = givesANumber2(); var ak2: string = givesANumber2(); + // Error: number ~> string var NumberGenerator2 = require(\"ES6_Named2\").NumberGenerator2; var al1: number = new NumberGenerator2().givesANumber(); var al2: string = new NumberGenerator2().givesANumber(); + // Error: number ~> string var varDeclNumber3 = require(\"ES6_Named2\").varDeclNumber3; var varDeclNumber4 = require(\"ES6_Named2\").varDeclNumber4; @@ -1103,20 +1144,24 @@ var am2: number = varDeclNumber4; var am3: string = varDeclNumber3; // Error: number ~> string var am4: string = varDeclNumber4; + // Error: number ~> string var numberValue6 = require(\"ES6_ExportFrom_Intermediary2\").numberValue1; var ap1: number = numberValue6; var ap2: string = numberValue6; + // Error: number ~> string var numberValue2_renamed2 = require( \"ES6_ExportFrom_Intermediary2\" ).numberValue2_renamed2; var aq1: number = numberValue2_renamed2; var aq2: string = numberValue2_renamed2; + // Error: number ~> string var numberValue7 = require(\"ES6_ExportAllFrom_Intermediary2\").numberValue2; var ar1: number = numberValue7; var ar2: string = numberValue7; + // Error: number ~> string //////////////////////////////////////////////////////// // == ES6 Default+Named -> ES6 import Default+Named== // @@ -1125,9 +1170,11 @@ import defaultNum, { str as namedStr } from \"./ES6_DefaultAndNamed\"; var as1: number = defaultNum; var as2: string = defaultNum; + // Error: number ~> string var as3: string = namedStr; var as4: number = namedStr; + // Error: string ~> number //////////////////////////////////////// // == Side-effect only ES6 imports == // @@ -1140,6 +1187,7 @@ import \"./SideEffects\"; import specifierNumber1 from \"ES6_Named1\"; // Error: Did you mean \`import {specifierNumber1} from ...\`? import { specifierNumber } from \"ES6_Named1\"; + // Error: Did you mean \`specifierNumber1\`? /////////////////////////////////////////////////// // == Multi \`export *\` should combine exports == // @@ -1151,6 +1199,7 @@ import { var at1: number = numberValue8; var at2: string = numberValue8; + // Error: number ~> string var at3: number = numberValue9; var at4: string = numberValue9; // Error: number ~> string diff --git a/tests/declare_module_exports/__snapshots__/jsfmt.spec.js.snap b/tests/declare_module_exports/__snapshots__/jsfmt.spec.js.snap index 698035b6..393964e1 100644 --- a/tests/declare_module_exports/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declare_module_exports/__snapshots__/jsfmt.spec.js.snap @@ -30,6 +30,7 @@ import declare_m_e_with_declare_var_e from \"declare_m_e_with_declare_var_e\"; import declare_module_exports from \"declare_module_exports\"; (declare_module_exports: number); (declare_module_exports: string); + // Error: number ~> string // Error: Has no named export \"str\"! import { str } from \"declare_m_e_with_other_value_declares\"; @@ -37,6 +38,7 @@ import { str } from \"declare_m_e_with_other_value_declares\"; import type { str2 } from \"declare_m_e_with_other_type_declares\"; (\"asdf\": str2); (42: str2); + // Error: number ~> string /** * \`declare var exports\` is deprecated, so we have a grace period where both @@ -45,6 +47,7 @@ import type { str2 } from \"declare_m_e_with_other_type_declares\"; import DEPRECATED__declare_var_exports from \"DEPRECATED__declare_var_exports\"; (DEPRECATED__declare_var_exports: number); (DEPRECATED__declare_var_exports: string); + // Error: number ~> string import declare_m_e_with_declare_var_e from \"declare_m_e_with_declare_var_e\"; (declare_m_e_with_declare_var_e: number); diff --git a/tests/declare_type/__snapshots__/jsfmt.spec.js.snap b/tests/declare_type/__snapshots__/jsfmt.spec.js.snap index 39b07834..d357e04c 100644 --- a/tests/declare_type/__snapshots__/jsfmt.spec.js.snap +++ b/tests/declare_type/__snapshots__/jsfmt.spec.js.snap @@ -43,9 +43,11 @@ var k1: baz = 42; var k2: baz = \"shab\"; // Error: string to int var k3: toz = foo(k1); + // works import type { toz } from \"ModuleAliasFoo\"; var k4: toz = foo(k1); + // works ////////////////////////////////////////////////////////// // == Declared Module with exports prop (issue 880) == // @@ -56,8 +58,10 @@ import type { Foo, Bar, Id } from \"foo\"; blah(0, 0); ({ toz: 3 }: Foo); + // error : {toz : number} ~> string (3: Bar); + // error : number ~> A (\"lol\": Id); // error : string ~> number " diff --git a/tests/def_site_variance/__snapshots__/jsfmt.spec.js.snap b/tests/def_site_variance/__snapshots__/jsfmt.spec.js.snap index 25a9fa8d..654e78b5 100644 --- a/tests/def_site_variance/__snapshots__/jsfmt.spec.js.snap +++ b/tests/def_site_variance/__snapshots__/jsfmt.spec.js.snap @@ -61,6 +61,7 @@ class PropVariance<+Out, -In> { +con1: Out; // ok +con2: In; + // error inv_dict1: { [k: string]: Out }; // error diff --git a/tests/destructuring/__snapshots__/jsfmt.spec.js.snap b/tests/destructuring/__snapshots__/jsfmt.spec.js.snap index 11bd677f..35522265 100644 --- a/tests/destructuring/__snapshots__/jsfmt.spec.js.snap +++ b/tests/destructuring/__snapshots__/jsfmt.spec.js.snap @@ -18,6 +18,7 @@ let [ b, ...zs ] = ys; let c = zs[0]; // retain tuple info let d = zs[1]; + // run off the end (a: void); // error: number ~> void @@ -26,6 +27,7 @@ let d = zs[1]; (c: void); // error: boolean ~> void (d: void); + // error: number|string|boolean ~> void let [ ...e ] = 0; " @@ -44,10 +46,12 @@ var { [\"key\"]: val3, ...spread } = { key: \"val\" }; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ var { [\"key\"]: val1 } = { key: \"val\" }; (val1: void); + // error: string ~> void var key: string = \"key\"; var { [key]: val2 } = { key: \"val\" }; (val2: void); + // ok (gasp!) by existing StrT -> ElemT rule var { [\"key\"]: val3, ...spread } = { key: \"val\" }; (spread.key: void); // error (gasp!) in general we don\'t know if a computed prop should be excluded from spread @@ -155,6 +159,7 @@ obj_prop_fun({}); obj_prop_fun({ p: {} }); // ok obj_prop_fun({ p: { q: null } }); + // ok, provides add\'l lower bound function obj_prop_var(o = { p: { q: \"\" } }) { var { p: { q = 0 } = { q: true } } = o; @@ -172,6 +177,7 @@ obj_prop_var({}); obj_prop_var({ p: {} }); // ok obj_prop_var({ p: { q: null } }); + // ok, provides add\'l lower bound function obj_rest( { p: { q, ...o } = { q: 0, r: 0 } } = { p: { q: 0, r: \"\" } } @@ -210,6 +216,7 @@ var { p: 0 }; (p: void); + // error: string ~> void function obj_prop_err({ x: { y } } = null) { } @@ -222,6 +229,7 @@ function arr_elem_err([ x ] = null) { // error: element 0 cannot be accessed on null function arr_rest_err([ ...a ] = null) { } + // error: expected array instead of null function gen(x: T, { p = x }: { p: T }): T { return p; @@ -231,6 +239,7 @@ function gen(x: T, { p = x }: { p: T }): T { obj_prop_fun(({}: { p?: { q?: null } })); // ok obj_prop_var(({}: { p?: { q?: null } })); + // ok // union-like upper bounds preserved through destructuring function obj_prop_opt({ p }: { p?: string } = { p: 0 }) { @@ -393,6 +402,7 @@ var bp1_err: string = baseprop1; // Error: number ~> string var bp2: number = others.baseprop2; var bp2_err: string = others.baseprop2; + // Error: number ~> string var cp1: number = childprop1; var cp1_err: string = childprop1; @@ -480,6 +490,7 @@ function obj_pattern({ prop }: { prop: X }) { type Prop = { prop: X }; function obj_pattern2({ prop }: Prop) { } + // prop: X function arr_pattern([ elem ]: X[]) { } @@ -487,6 +498,7 @@ function arr_pattern([ elem ]: X[]) { type Elem = X[]; function arr_pattern2([ elem ]: Elem) { } + // elem: X function tup_pattern([ proj ]: [X]) { } @@ -494,12 +506,14 @@ function tup_pattern([ proj ]: [X]) { type Proj = [X]; function tup_pattern2([ proj ]: Proj) { } + // proj: X function rest_antipattern(...t: T) { } // nonsense function rest_pattern(...r: X[]) { } + // r: X[] function obj_rest_pattern({ _, ...o }: { _: any, x: X }) { // o: { x: X } @@ -576,6 +590,7 @@ var { \"with-dash\": with_dash } = { \"with-dash\": \"motivating example\" }; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ var { key: val } = { key: \"val\" }; (val: void); + // error: string ~> void var { \"with-dash\": with_dash } = { \"with-dash\": \"motivating example\" }; (with_dash: \"motivating example\"); // ok diff --git a/tests/dictionary/__snapshots__/jsfmt.spec.js.snap b/tests/dictionary/__snapshots__/jsfmt.spec.js.snap index fd281fbf..db16d7f0 100644 --- a/tests/dictionary/__snapshots__/jsfmt.spec.js.snap +++ b/tests/dictionary/__snapshots__/jsfmt.spec.js.snap @@ -475,8 +475,10 @@ function unification_dict_values_invariant(x: Array<{ [k: string]: B }>) { let a: Array<{ [k: string]: A }> = x; // error a[0].p = new A(); + // in[0].p no longer B let b: Array<{ [k: string]: B }> = x; + // ok let c: Array<{ [k: string]: C }> = x; // error @@ -487,8 +489,10 @@ function subtype_dict_values_invariant(x: { [k: string]: B }) { let a: { [k: string]: A } = x; // error a.p = new A(); + // x[0].p no longer B let b: { [k: string]: B } = x; + // ok let c: { [k: string]: C } = x; // error @@ -551,8 +555,10 @@ function unification_mix_with_declared_props_invariant_l( let a: Array<{ [k: string]: B, p: A }> = x; // error: A ~> B a[0].p = new A(); + // x[0].p no longer B let b: Array<{ [k: string]: B, p: B }> = x; + // ok let c: Array<{ [k: string]: B, p: C }> = x; // error @@ -567,8 +573,10 @@ function unification_mix_with_declared_props_invariant_r( let a: Array<{ [k: string]: A }> = xa; // error a[0].p = new A(); + // xa[0].p no longer B let b: Array<{ [k: string]: B }> = xb; + // ok let c: Array<{ [k: string]: C }> = xc; // error @@ -579,8 +587,10 @@ function subtype_mix_with_declared_props_invariant_l(x: { [k: string]: B }) { let a: { [k: string]: B, p: A } = x; // error: A ~> B a.p = new A(); + // x.p no longer B let b: { [k: string]: B, p: B } = x; + // ok let c: { [k: string]: B, p: C } = x; // error @@ -595,8 +605,10 @@ function subtype_mix_with_declared_props_invariant_r( let a: { [k: string]: A } = xa; // error a.p = new A(); + // xa.p no longer B let b: { [k: string]: B } = xb; + // ok let c: { [k: string]: C } = xc; // error @@ -619,8 +631,10 @@ function subtype_dict_to_obj(x: { [k: string]: B }) { let a: { p: A } = x; // error a.p = new A(); + // x.p no longer B let b: { p: B } = x; + // ok let c: { p: C } = x; // error @@ -631,6 +645,7 @@ function subtype_obj_to_dict(x: { p: B }) { let a: { [k: string]: A } = x; // error a.p = new A(); + // x.p no longer B let b: { [k: string]: B } = x; @@ -759,11 +774,13 @@ var x: { [key: string]: string } = {}; var y: { [key: string]: number } = x; // 2 errors, number !~> string & vice versa var z: { [key: number]: string } = x; + // 2 errors, string !~> number & vice versa var a: { [key: string]: ?string } = {}; var b: { [key: string]: string } = a; // 2 errors (null & undefined) var c: { [key: string]: ?string } = b; + // 2 errors, since c[\'x\'] = null updates b // 2 errors (number !~> string, string !~> number) function foo0( diff --git a/tests/dom/__snapshots__/jsfmt.spec.js.snap b/tests/dom/__snapshots__/jsfmt.spec.js.snap index d4395626..7bb8e615 100644 --- a/tests/dom/__snapshots__/jsfmt.spec.js.snap +++ b/tests/dom/__snapshots__/jsfmt.spec.js.snap @@ -240,6 +240,7 @@ const a = new URL(\"http://flowtype.org/\"); const b = new URL(\"/docs\", a); // correct const c = new URL(\"/docs\", \"http://flowtype.org/\"); + // correct const d: URLSearchParams = c.searchParams; // correct diff --git a/tests/encaps/__snapshots__/jsfmt.spec.js.snap b/tests/encaps/__snapshots__/jsfmt.spec.js.snap index 631e98f4..b453ab55 100644 --- a/tests/encaps/__snapshots__/jsfmt.spec.js.snap +++ b/tests/encaps/__snapshots__/jsfmt.spec.js.snap @@ -19,6 +19,7 @@ var s3 = tag2 \`la la la\`; class A {} var a = new A(); var s1 = \`l\${a.x}r\`; + // error: no prop x in A function tag(strings, ...values) { var x: number = strings[0]; diff --git a/tests/enumerror/__snapshots__/jsfmt.spec.js.snap b/tests/enumerror/__snapshots__/jsfmt.spec.js.snap index b6817b88..0d7407ac 100644 --- a/tests/enumerror/__snapshots__/jsfmt.spec.js.snap +++ b/tests/enumerror/__snapshots__/jsfmt.spec.js.snap @@ -33,14 +33,12 @@ function isActive( ): boolean { return ad.state === \"ACTIVE\"; } - isActive({ state: \"PAUSE\" }); var MyStates = { PAUSED: \"PAUSED\", ACTIVE: \"ACTIVE\", DELETED: \"DELETED\" }; function isActive2(ad: { state: $Keys }): boolean { return ad.state === MyStates.ACTIVE; } - isActive2({ state: \"PAUSE\" }); type Keys = $Keys<{ x: any, y: any }>; diff --git a/tests/equals/__snapshots__/jsfmt.spec.js.snap b/tests/equals/__snapshots__/jsfmt.spec.js.snap index 5d48ea58..f6bd4860 100644 --- a/tests/equals/__snapshots__/jsfmt.spec.js.snap +++ b/tests/equals/__snapshots__/jsfmt.spec.js.snap @@ -21,6 +21,7 @@ null == 1; 1 == \"\"; // error \"\" == 1; + // error var x = (null: ?number); x == 1; diff --git a/tests/es6modules/__snapshots__/jsfmt.spec.js.snap b/tests/es6modules/__snapshots__/jsfmt.spec.js.snap index b04c6bf6..3d36a053 100644 --- a/tests/es6modules/__snapshots__/jsfmt.spec.js.snap +++ b/tests/es6modules/__snapshots__/jsfmt.spec.js.snap @@ -164,7 +164,6 @@ export default class { return 42; } } - " `; @@ -186,7 +185,6 @@ export default class { return 42; } } - " `; @@ -277,7 +275,6 @@ export default class Foo { return 42; } } - " `; @@ -536,7 +533,6 @@ export { groupedSpecifierNumber1, groupedSpecifierNumber2 }; export function givesANumber(): number { return 42; } - export class NumberGenerator { givesANumber(): number { return 42; @@ -588,7 +584,6 @@ export { groupedSpecifierNumber3, groupedSpecifierNumber4 }; export function givesANumber2(): number { return 42; } - export class NumberGenerator2 { givesANumber(): number { return 42; @@ -997,36 +992,44 @@ import {typeAlias} from \"./ExportType\"; // Error: Cannot vanilla-import a type import * as DefaultA from \"A\"; var a1: number = DefaultA.numberValue1; var a2: string = DefaultA.numberValue1; + // Error: number ~> string // File path import * as DefaultB from \"./B\"; var b1: number = DefaultB.numberValue; var b2: string = DefaultB.numberValue; + // Error: number ~> string // C.js exists, but not as a providesModule import DefaultC from \"C\"; + // Error: No such module // @providesModule D exists, but not as a filename import DefaultD from \"./D\"; + // Error: No such module // ================================================ // // == CommonJS Clobbering Literal Exports -> ES6 == // // ================================================ // import { doesntExist1 } from \"CommonJS_Clobbering_Lit\"; + // Error: Not an exported binding import { numberValue1 } from \"CommonJS_Clobbering_Lit\"; var c1: number = numberValue1; var c2: string = numberValue1; + // Error: number ~> string import { numberValue2 as numVal1 } from \"CommonJS_Clobbering_Lit\"; var d1: number = numVal1; var d2: string = numVal1; + // Error: number ~> string import CJS_Clobb_Lit from \"CommonJS_Clobbering_Lit\"; var e1: number = CJS_Clobb_Lit.numberValue3; var e2: string = CJS_Clobb_Lit.numberValue3; // Error: number ~> string CJS_Clobb_Lit.doesntExist; + // Error: doesntExist isn\'t a property import * as CJS_Clobb_Lit_NS from \"CommonJS_Clobbering_Lit\"; var f1: number = CJS_Clobb_Lit_NS.numberValue4; @@ -1036,17 +1039,20 @@ CJS_Clobb_Lit_NS.default.default; var f3: string = CJS_Clobb_Lit_NS.numberValue4; // Error: number ~> string var f4: string = CJS_Clobb_Lit_NS.default.numberValue5; + // Error: number ~> string // ============================================== // // == CommonJS Clobbering Class Exports -> ES6 == // // ============================================== // import { doesntExist2 } from \"CommonJS_Clobbering_Class\"; + // Error: Not an exported binding // The following import should error because class statics are not turned into // named exports for now. This avoids complexities with polymorphic static // members (where the polymophism is defined on the class itself rather than the // method). import { staticNumber1, baseProp, childProp } from \"CommonJS_Clobbering_Class\"; + // Error import CJS_Clobb_Class from \"CommonJS_Clobbering_Class\"; new CJS_Clobb_Class(); @@ -1057,6 +1063,7 @@ var h2: string = CJS_Clobb_Class.staticNumber2(); // Error: number ~> string var h3: number = new CJS_Clobb_Class().instNumber1(); var h4: string = new CJS_Clobb_Class().instNumber1(); + // Error: number ~> string import * as CJS_Clobb_Class_NS from \"CommonJS_Clobbering_Class\"; new CJS_Clobb_Class_NS(); @@ -1065,69 +1072,84 @@ var i1: number = CJS_Clobb_Class_NS.staticNumber3(); // Error: Class statics not copied to Namespace object var i2: number = new CJS_Clobb_Class_NS.default().instNumber2(); var i3: string = new CJS_Clobb_Class_NS.default().instNumber2(); + // Error: number ~> string // =================================== // // == CommonJS Named Exports -> ES6 == // // =================================== // import { doesntExist3 } from \"CommonJS_Named\"; + // Error: Not an exported binding import { numberValue2 } from \"CommonJS_Named\"; var j1: number = numberValue2; var j2: string = numberValue2; + // Error: number ~> string import { numberValue3 as numVal3 } from \"CommonJS_Named\"; var k1: number = numVal3; var k2: string = numVal3; + // Error: number ~> string import * as CJS_Named from \"CommonJS_Named\"; var l1: number = CJS_Named.numberValue1; var l2: string = CJS_Named.numberValue1; // Error: number ~> string CJS_Named.doesntExist; + // Error: doesntExist isn\'t a property import * as CJS_Named_NS from \"CommonJS_Named\"; var m1: number = CJS_Named_NS.numberValue4; var m2: string = CJS_Named_NS.default.numberValue4; // Error: CommonJS_Named has no default export var m3: string = CJS_Named_NS.numberValue4; + // Error: number ~> string ////////////////////////////// // == ES6 Default -> ES6 == // ////////////////////////////// import { doesntExist4 } from \"ES6_Default_AnonFunction1\"; + // Error: Not an exported binding import ES6_Def_AnonFunc1 from \"ES6_Default_AnonFunction1\"; var n1: number = ES6_Def_AnonFunc1(); var n2: string = ES6_Def_AnonFunc1(); + // Error: number ~> string import ES6_Def_NamedFunc1 from \"ES6_Default_NamedFunction1\"; var o1: number = ES6_Def_NamedFunc1(); var o2: string = ES6_Def_NamedFunc1(); + // Error: number ~> string import ES6_Def_AnonClass1 from \"ES6_Default_AnonClass1\"; var p1: number = new ES6_Def_AnonClass1().givesANum(); var p2: string = new ES6_Def_AnonClass1().givesANum(); + // Error: number ~> string import ES6_Def_NamedClass1 from \"ES6_Default_NamedClass1\"; var q1: number = new ES6_Def_NamedClass1().givesANum(); var q2: string = new ES6_Def_NamedClass1().givesANum(); + // Error: number ~> string //////////////////////////// // == ES6 Named -> ES6 == // //////////////////////////// import doesntExist5 from \"ES6_Named1\"; + // Error: Not an exported binding import { specifierNumber1 as specifierNumber1_1 } from \"ES6_Named1\"; var r1: number = specifierNumber1_1; var r2: string = specifierNumber1_1; + // Error: number ~> string import { specifierNumber2Renamed } from \"ES6_Named1\"; var s1: number = specifierNumber2Renamed; var s2: string = specifierNumber2Renamed; + // Error: number ~> string import { specifierNumber3 as specifierNumber3Renamed } from \"ES6_Named1\"; var t1: number = specifierNumber3Renamed; var t2: string = specifierNumber3Renamed; + // Error: number ~> string import { groupedSpecifierNumber1, groupedSpecifierNumber2 } from \"ES6_Named1\"; var u1: number = groupedSpecifierNumber1; @@ -1135,14 +1157,17 @@ var u2: number = groupedSpecifierNumber2; var u3: string = groupedSpecifierNumber1; // Error: number ~> string var u4: string = groupedSpecifierNumber2; + // Error: number ~> string import { givesANumber } from \"ES6_Named1\"; var v1: number = givesANumber(); var v2: string = givesANumber(); + // Error: number ~> string import { NumberGenerator } from \"ES6_Named1\"; var w1: number = new NumberGenerator().givesANumber(); var w2: string = new NumberGenerator().givesANumber(); + // Error: number ~> string import { varDeclNumber1, varDeclNumber2 } from \"ES6_Named1\"; var x1: number = varDeclNumber1; @@ -1150,47 +1175,58 @@ var x2: number = varDeclNumber2; var x3: string = varDeclNumber1; // Error: number ~> string var x4: string = varDeclNumber2; + // Error: number ~> string import { destructuredObjNumber } from \"ES6_Named1\"; var y1: number = destructuredObjNumber; var y2: string = destructuredObjNumber; + // Error: number ~> string import { destructuredArrNumber } from \"ES6_Named1\"; var z1: number = destructuredArrNumber; var z2: string = destructuredArrNumber; + // Error: number ~> string import { numberValue1 as numberValue4 } from \"ES6_ExportFrom_Intermediary1\"; var aa1: number = numberValue4; var aa2: string = numberValue4; + // Error: number ~> string import { numberValue2_renamed } from \"ES6_ExportFrom_Intermediary1\"; var ab1: number = numberValue2_renamed; var ab2: string = numberValue2_renamed; + // Error: number ~> string import { numberValue1 as numberValue5 } from \"ES6_ExportAllFrom_Intermediary1\"; var ac1: number = numberValue5; var ac2: string = numberValue5; + // Error: number ~> string /////////////////////////////////// // == ES6 Default -> CommonJS == // /////////////////////////////////// require(\"ES6_Default_AnonFunction2\").doesntExist; + // Error: \'doesntExist\' isn\'t an export var ES6_Def_AnonFunc2 = require(\"ES6_Default_AnonFunction2\").default; var ad1: number = ES6_Def_AnonFunc2(); var ad2: string = ES6_Def_AnonFunc2(); + // Error: number ~> string var ES6_Def_NamedFunc2 = require(\"ES6_Default_NamedFunction2\").default; var ae1: number = ES6_Def_NamedFunc2(); var ae2: string = ES6_Def_NamedFunc2(); + // Error: number ~> string var ES6_Def_AnonClass2 = require(\"ES6_Default_AnonClass2\").default; var af1: number = new ES6_Def_AnonClass2().givesANum(); var af2: string = new ES6_Def_AnonClass2().givesANum(); + // Error: number ~> string var ES6_Def_NamedClass2 = require(\"ES6_Default_NamedClass2\").default; var ag1: number = new ES6_Def_NamedClass2().givesANum(); var ag2: string = new ES6_Def_NamedClass2().givesANum(); + // Error: number ~> string ///////////////////////////////// // == ES6 Named -> CommonJS == // @@ -1198,10 +1234,12 @@ var ag2: string = new ES6_Def_NamedClass2().givesANum(); var specifierNumber4 = require(\"ES6_Named2\").specifierNumber4; var ah1: number = specifierNumber4; var ah2: string = specifierNumber4; + // Error: number ~> string var specifierNumber5Renamed = require(\"ES6_Named2\").specifierNumber5Renamed; var ai1: number = specifierNumber5Renamed; var ai2: string = specifierNumber5Renamed; + // Error: number ~> string var groupedSpecifierNumber3 = require(\"ES6_Named2\").groupedSpecifierNumber3; var groupedSpecifierNumber4 = require(\"ES6_Named2\").groupedSpecifierNumber4; @@ -1210,14 +1248,17 @@ var aj2: number = groupedSpecifierNumber4; var aj3: string = groupedSpecifierNumber3; // Error: number ~> string var aj4: string = groupedSpecifierNumber4; + // Error: number ~> string var givesANumber2 = require(\"ES6_Named2\").givesANumber2; var ak1: number = givesANumber2(); var ak2: string = givesANumber2(); + // Error: number ~> string var NumberGenerator2 = require(\"ES6_Named2\").NumberGenerator2; var al1: number = new NumberGenerator2().givesANumber(); var al2: string = new NumberGenerator2().givesANumber(); + // Error: number ~> string var varDeclNumber3 = require(\"ES6_Named2\").varDeclNumber3; var varDeclNumber4 = require(\"ES6_Named2\").varDeclNumber4; @@ -1226,28 +1267,34 @@ var am2: number = varDeclNumber4; var am3: string = varDeclNumber3; // Error: number ~> string var am4: string = varDeclNumber4; + // Error: number ~> string var destructuredObjNumber2 = require(\"ES6_Named2\").destructuredObjNumber2; var an1: number = destructuredObjNumber2; var an2: string = destructuredObjNumber2; + // Error: number ~> string var destructuredArrNumber2 = require(\"ES6_Named2\").destructuredArrNumber2; var ao1: number = destructuredArrNumber2; var ao2: string = destructuredArrNumber2; + // Error: number ~> string var numberValue6 = require(\"ES6_ExportFrom_Intermediary2\").numberValue1; var ap1: number = numberValue6; var ap2: string = numberValue6; + // Error: number ~> string var numberValue2_renamed2 = require( \"ES6_ExportFrom_Intermediary2\" ).numberValue2_renamed2; var aq1: number = numberValue2_renamed2; var aq2: string = numberValue2_renamed2; + // Error: number ~> string var numberValue7 = require(\"ES6_ExportAllFrom_Intermediary2\").numberValue2; var ar1: number = numberValue7; var ar2: string = numberValue7; + // Error: number ~> string //////////////////////////////////////////////////////// // == ES6 Default+Named -> ES6 import Default+Named== // @@ -1256,9 +1303,11 @@ import defaultNum, { str as namedStr } from \"./ES6_DefaultAndNamed\"; var as1: number = defaultNum; var as2: string = defaultNum; + // Error: number ~> string var as3: string = namedStr; var as4: number = namedStr; + // Error: string ~> number //////////////////////////////////////// // == Side-effect only ES6 imports == // @@ -1271,6 +1320,7 @@ import \"./SideEffects\"; import specifierNumber1 from \"ES6_Named1\"; // Error: Did you mean \`import {specifierNumber1} from ...\`? import { specifierNumber } from \"ES6_Named1\"; + // Error: Did you mean \`specifierNumber1\`? /////////////////////////////////////////////////// // == Multi \`export *\` should combine exports == // @@ -1282,9 +1332,11 @@ import { var at1: number = numberValue8; var at2: string = numberValue8; + // Error: number ~> string var at3: number = numberValue9; var at4: string = numberValue9; + // Error: number ~> string ///////////////////////////////////////////////////////////// // == Vanilla \`import\` cannot import a type-only export == // @@ -1358,28 +1410,34 @@ function testRequires() { // CommonJS module import * as DefaultA from \"A\"; DefaultA.numberValue1 = 123; + // Error: DefaultA is frozen // ES6 module import * as ES6_Named1 from \"ES6_Named1\"; ES6_Named1.varDeclNumber1 = 123; + // Error: ES6_Named1 is frozen // CommonJS module that clobbers module.exports import * as CommonJS_Star from \"CommonJS_Clobbering_Lit\"; CommonJS_Star.numberValue1 = 123; // Error: frozen CommonJS_Star.default.numberValue1 = 123; + // ok import CommonJS_Clobbering_Lit from \"CommonJS_Clobbering_Lit\"; CommonJS_Clobbering_Lit.numberValue1 = 123; + // ok // CommonJS module that clobbers module.exports with a frozen object import * as CommonJS_Frozen_Star from \"CommonJS_Clobbering_Frozen\"; CommonJS_Frozen_Star.numberValue1 = 123; // Error: frozen CommonJS_Frozen_Star.default.numberValue1 = 123; + // Error: frozen import CommonJS_Clobbering_Frozen from \"CommonJS_Clobbering_Frozen\"; CommonJS_Clobbering_Frozen.numberValue1 = 123; + // Error: exports are frozen // // Requires @@ -1388,14 +1446,17 @@ function testRequires() { // CommonJS module var DefaultA = require(\"A\"); DefaultA.numberValue1 = 123; + // ok, not frozen by default // ES6 module var ES6_Named1 = require(\"ES6_Named1\"); ES6_Named1.numberValue = 123; + // error, es6 exports are frozen // CommonJS module that clobbers module.exports var CommonJS_Star = require(\"CommonJS_Clobbering_Lit\"); CommonJS_Star.numberValue1 = 123; + // ok, not frozen by default // CommonJS module that clobbers module.exports with a frozen object var CommonJS_Frozen_Star = require(\"CommonJS_Clobbering_Frozen\"); diff --git a/tests/es_declare_module/__snapshots__/jsfmt.spec.js.snap b/tests/es_declare_module/__snapshots__/jsfmt.spec.js.snap index 0a41dc33..14199a82 100644 --- a/tests/es_declare_module/__snapshots__/jsfmt.spec.js.snap +++ b/tests/es_declare_module/__snapshots__/jsfmt.spec.js.snap @@ -53,6 +53,7 @@ import CJS_Named from \"CJS_Named\"; // Error: string ~> number (CJS_Named: { num1: number, str1: string }); (CJS_Named: number); + // Error: Module ~> number import { num2 } from \"CJS_Clobbered\"; // Error: No such export! @@ -63,16 +64,19 @@ import { numExport } from \"CJS_Clobbered\"; import type { numType } from \"CJS_Clobbered\"; (42: numType); (\"asdf\": numType); + // Error: string ~> number import { strHidden } from \"ES\"; // Error: No such export! import { str3 } from \"ES\"; (str3: string); (str3: number); + // Error: string ~> number import { num3 } from \"ES\"; (num3: number); (num3: string); + // Error: number ~> string import { C } from \"ES\"; import type { C as CType } from \"ES\"; @@ -81,12 +85,14 @@ import type { C as CType } from \"ES\"; // Error: number ~> C (new C(): CType); (42: CType); + // Error: number ~> CType import { T } from \"ES\"; // Error: T is a type import, not a value import type { T as T2 } from \"ES\"; (42: T2); (\"asdf\": T2); + // Error: string ~> number import { exports as nope } from \"ES\"; // Error: Not an export " diff --git a/tests/esproposal_export_star_as.enable/__snapshots__/jsfmt.spec.js.snap b/tests/esproposal_export_star_as.enable/__snapshots__/jsfmt.spec.js.snap index 2562ba33..4ab089e5 100644 --- a/tests/esproposal_export_star_as.enable/__snapshots__/jsfmt.spec.js.snap +++ b/tests/esproposal_export_star_as.enable/__snapshots__/jsfmt.spec.js.snap @@ -15,6 +15,7 @@ import { source } from \"./test\"; var a: number = source.num; var b: string = source.num; + // Error: num ~> string var c: string = source.str; var d: number = source.str; // Error: num ~> string diff --git a/tests/esproposal_export_star_as.ignore/__snapshots__/jsfmt.spec.js.snap b/tests/esproposal_export_star_as.ignore/__snapshots__/jsfmt.spec.js.snap index c55d3f04..fa8ea6fd 100644 --- a/tests/esproposal_export_star_as.ignore/__snapshots__/jsfmt.spec.js.snap +++ b/tests/esproposal_export_star_as.ignore/__snapshots__/jsfmt.spec.js.snap @@ -15,6 +15,7 @@ import { source } from \"./test\"; var a: number = source.num; var b: string = source.num; + // Error: num ~> string var c: string = source.str; var d: number = source.str; // Ignored error: num ~> string diff --git a/tests/export_type/__snapshots__/jsfmt.spec.js.snap b/tests/export_type/__snapshots__/jsfmt.spec.js.snap index 154c9405..ef5cb1df 100644 --- a/tests/export_type/__snapshots__/jsfmt.spec.js.snap +++ b/tests/export_type/__snapshots__/jsfmt.spec.js.snap @@ -60,24 +60,30 @@ import type { var a: inlinedType1 = 42; var b: inlinedType1 = \"asdf\"; + // Error: string ~> number var c: standaloneType1 = 42; var d: standaloneType1 = \"asdf\"; + // Error: string ~> number var e: talias1 = 42; var f: talias1 = \"asdf\"; + // Error: string ~> number var g: talias3 = 42; var h: talias3 = \"asdf\"; + // Error: string ~> number import type { talias4 } from \"./cjs_with_types\"; var i: talias4 = 42; var j: talias4 = \"asdf\"; + // Error: string ~> number import { IFoo, IFoo2 } from \"./types_only\"; var k: IFoo = { prop: 42 }; var l: IFoo = { prop: \"asdf\" }; + // Error: {prop:string} ~> {prop:number} var m: IFoo2 = { prop: \"asdf\" }; var n: IFoo2 = { prop: 42 }; // Error: {prop:number} ~> {prop:string} @@ -106,17 +112,18 @@ export interface IFoo { prop: number }; export type inlinedType1 = number; var a: inlinedType1 = 42; var b: inlinedType1 = \"asdf\"; + // Error: string ~> number type standaloneType1 = number; export type { standaloneType1 }; type standaloneType2 = number; export { standaloneType2 }; + // Error: Missing \`type\` keyword export type { talias1, talias2 as talias3, IFoo2 } from \"./types_only2\"; export interface IFoo { prop: number } - " `; @@ -132,6 +139,5 @@ export interface IFoo2 { prop: string }; export type talias1 = number; export type talias2 = number; export interface IFoo2 { prop: string } - " `; diff --git a/tests/fetch/__snapshots__/jsfmt.spec.js.snap b/tests/fetch/__snapshots__/jsfmt.spec.js.snap index 9a12618a..d045bb4b 100644 --- a/tests/fetch/__snapshots__/jsfmt.spec.js.snap +++ b/tests/fetch/__snapshots__/jsfmt.spec.js.snap @@ -35,6 +35,7 @@ const myRequest = new Request(\"http://google.com\"); const a: Promise = fetch(myRequest).then(response => response.text()); const b: Promise = fetch(myRequest); + // incorrect var myInit = { method: \"GET\", @@ -44,6 +45,7 @@ var myInit = { }; const c: Promise = fetch(\"image.png\").then(response => response.blob()); + // correct const d: Promise = fetch(\"image.png\"); // incorrect " @@ -102,12 +104,15 @@ e.set(\"Content-Type\", \"image/jpeg\"); e.set(\"Content-Type\"); // not correct e.set({ \"Content-Type\", \"image/jpeg\" }); + // not correct const f: Headers = e.append(\"Content-Type\", \"image/jpeg\"); + // not correct const g: string = e.get(\"Content-Type\"); // correct const h: number = e.get(\"Content-Type\"); + // not correct for (let v of e) { const [ i, j ]: [string, string] = v; // correct @@ -185,10 +190,12 @@ const c: Request = new Request(b); const d: Request = new Request(c.clone()); // correct (doesn\'t make much sense though) const e: Request = new Request(b, c); + // incorrect const f: Request = new Request({}); // incorrect const g: Request = new Request(\"http://example.org\", {}); + // correct const h: Request = new Request(\"http://example.org\", { method: \"GET\", @@ -196,6 +203,7 @@ const h: Request = new Request(\"http://example.org\", { mode: \"cors\", cache: \"default\" }); + // correct const i: Request = new Request(\"http://example.org\", { method: \"POST\", @@ -204,6 +212,7 @@ const i: Request = new Request(\"http://example.org\", { mode: \"cors\", cache: \"default\" }); + // correct const j: Request = new Request(\"http://example.org\", { method: \"GET\", @@ -211,6 +220,7 @@ const j: Request = new Request(\"http://example.org\", { mode: \"cors\", cache: \"default\" }); + // incorrect - headers is string const k: Request = new Request(\"http://example.org\", { method: \"CONNECT\", @@ -218,6 +228,7 @@ const k: Request = new Request(\"http://example.org\", { mode: \"cors\", cache: \"default\" }); + // incorrect - CONNECT is forbidden var l: boolean = h.bodyUsed; @@ -285,30 +296,37 @@ const a: Response = new Response(); const b: Response = new Response(new Blob()); // correct const c: Response = new Response(new FormData()); + // correct const d: Response = new Response(new FormData(), { status: 404 }); + // correct const e: Response = new Response(\"responsebody\", { status: \"404\" }); + // incorrect const f: Response = new Response(\"responsebody\", { status: 404, headers: \"\'Content-Type\': \'image/jpeg\'\" }); + // incorrect const g: Response = new Response(\"responsebody\", { status: 404, headers: { \"Content-Type\": \"image/jpeg\" } }); + // correct const h: Response = new Response(\"responsebody\", { status: 404, headers: new Headers({ \"Content-Type\": \"image/jpeg\" }) }); + // correct, if verbose const i: Response = new Response({ status: 404, headers: new Headers({ \"Content-Type\": \"image/jpeg\" }) }); + // incorrect const ok: boolean = h.ok; const status: number = h.status; @@ -376,12 +394,15 @@ e.set(\"key1\", \"value1\"); e.set(\"key1\"); // not correct e.set({ \"key1\", \"value1\" }); + // not correct const f: URLSearchParams = e.append(\"key1\", \"value1\"); + // not correct const g: string = e.get(\"key1\"); // correct const h: number = e.get(\"key1\"); + // not correct for (let v of e) { const [ i, j ]: [string, string] = v; // correct diff --git a/tests/fixpoint/__snapshots__/jsfmt.spec.js.snap b/tests/fixpoint/__snapshots__/jsfmt.spec.js.snap index bca252bb..d5449747 100644 --- a/tests/fixpoint/__snapshots__/jsfmt.spec.js.snap +++ b/tests/fixpoint/__snapshots__/jsfmt.spec.js.snap @@ -35,7 +35,6 @@ module.exports = {fn: fix}; function eq(x: number, y: number) { return true; } - function sub(x: number, y: number) { return 0; } diff --git a/tests/function/__snapshots__/jsfmt.spec.js.snap b/tests/function/__snapshots__/jsfmt.spec.js.snap index cb2af2b5..8c581f24 100644 --- a/tests/function/__snapshots__/jsfmt.spec.js.snap +++ b/tests/function/__snapshots__/jsfmt.spec.js.snap @@ -51,14 +51,17 @@ test.apply(\"\", [ \"\", 0 ]); // wrong this is an error test.apply(0, [ \"\", 0 ]); + // error: lookup \`length\` on Number // not enough arguments is an error (via incompatible RestT) test.apply(\"\", [ \"\" ]); + // error: string ~> number // mistyped arguments is an error test.apply(\"\", [ \"\", \"\" ]); // error: string ~> number (2nd arg) test.apply(\"\", [ 0, 0 ]); + // error: number ~> string (1st arg) // resolve args array from tvar function f(args) { @@ -69,9 +72,11 @@ f([ \"\", 0 ]); f([ \"\", \"\" ]); // error: string ~> number (2nd arg) f([ 0, 0 ]); + // error: number ~> string (1st arg) // expect array test.apply(\"\", \"not array\"); + // error: expect array of args // expect 4 errors: // - lookup length on Number (because 0 is used as \`this\`) @@ -166,14 +171,17 @@ test.call(\"\", \"\", 0); // wrong this is an error test.call(0, \"\", 0); + // error: lookup \`length\` on Number // not enough arguments is an error (via incompatible RestT) test.call(\"\", \"\"); + // error: string ~> number // mistyped arguments is an error test.call(\"\", \"\", \"\"); // error: string ~> number (2nd arg) test.call(\"\", 0, 0); + // error: number ~> string (1st arg) // resolve args array from tvar function f(args) { @@ -184,6 +192,7 @@ f([ \"\", 0 ]); f([ \"\", \"\" ]); // error: string ~> number (2nd arg) f([ 0, 0 ]); + // error: number ~> string (1st arg) // expect 3 errors: // - lookup length on Number (0 used as \`this\`) @@ -315,6 +324,7 @@ let tests = [ (y.length: void); // error, it\'s a number (z.length: void); + // error, it\'s a number (x.name: void); // error, it\'s a string @@ -330,12 +340,14 @@ let tests = [ y.length = \"foo\"; // error, it\'s a number z.length = \"foo\"; + // error, it\'s a number x.name = 123; // error, it\'s a string y.name = 123; // error, it\'s a string z.name = 123; + // error, it\'s a string // Non-(Function.prototype) properties on a \`Function\` type should be \`any\` (z.foo: number); diff --git a/tests/generators/__snapshots__/jsfmt.spec.js.snap b/tests/generators/__snapshots__/jsfmt.spec.js.snap index c4453cee..65022150 100644 --- a/tests/generators/__snapshots__/jsfmt.spec.js.snap +++ b/tests/generators/__snapshots__/jsfmt.spec.js.snap @@ -231,6 +231,7 @@ var examples = new GeneratorExamples(); for (var x of examples.infer_stmt()) { (x: string); } + // error: number ~> string var infer_stmt_next = examples.infer_stmt().next(0).value; // error: number ~> boolean @@ -259,6 +260,7 @@ for (var x of examples.delegate_yield_generator()) { } examples.delegate_next_iterable([]).next(\"\"); + // error: Iterator has no next value for (var x of examples.delegate_yield_iterable([])) { (x: string); // error: number ~> string @@ -303,8 +305,10 @@ var examples = new GeneratorExamples(); for (var x of examples.infer_stmt()) { (x: string); } + // error: number ~> string var infer_stmt_next = examples.infer_stmt().next(0).value; + // error: number ~> boolean if (typeof infer_stmt_next === \"undefined\") { } else if (typeof infer_stmt_next === \"number\") { @@ -544,6 +548,7 @@ function* delegate_next_iterable(xs: Array) { yield* xs; } delegate_next_iterable([]).next(\"\"); + // error: Iterator has no next value function* delegate_yield_iterable(xs: Array) { yield* xs; diff --git a/tests/get-def2/__snapshots__/jsfmt.spec.js.snap b/tests/get-def2/__snapshots__/jsfmt.spec.js.snap index f1ef4235..63c114aa 100644 --- a/tests/get-def2/__snapshots__/jsfmt.spec.js.snap +++ b/tests/get-def2/__snapshots__/jsfmt.spec.js.snap @@ -44,15 +44,18 @@ var Parent = require(\"./Parent\"); let ParentFoo; ({ ParentFoo } = Parent); ParentFoo; + // Points to lval in line above this // Follows assignment on simple/\"non-destructuring\" patterns let ParentFoo2; ParentFoo2 = Parent; ParentFoo2; + // Points to LHS of line above this // Follows assignment with declaration let ParentFoo3 = Parent; ParentFoo3; + // Points to LHS of line above this // Follows non-destructured property access of \`require(\'Parent\')\` let foo = require(\"./Parent\").ParentFoo.foo; diff --git a/tests/getters_and_setters_enabled/__snapshots__/jsfmt.spec.js.snap b/tests/getters_and_setters_enabled/__snapshots__/jsfmt.spec.js.snap index 41bc8268..dde3dd87 100644 --- a/tests/getters_and_setters_enabled/__snapshots__/jsfmt.spec.js.snap +++ b/tests/getters_and_setters_enabled/__snapshots__/jsfmt.spec.js.snap @@ -101,6 +101,7 @@ class Foo { } set propWithMismatchingGetterAndSetter(x: string) { } + // doesn\'t match getter (OK) propOverriddenWithGetter: number; get propOverriddenWithGetter() { @@ -121,6 +122,7 @@ var testGetterNoError2: number = foo.goodGetterWithAnnotation; var testGetterWithError1: string = foo.goodGetterNoAnnotation; // Error number ~> string var testGetterWithError2: string = foo.goodGetterWithAnnotation; + // Error number ~> string // Test setting properties with getters foo.goodSetterNoAnnotation = 123; @@ -130,8 +132,10 @@ foo.goodSetterWithAnnotation = 123; foo.goodSetterNoAnnotation = \"hello\"; // Error string ~> number foo.goodSetterWithAnnotation = \"hello\"; + // Error string ~> number var testSubtypingGetterAndSetter: number = foo.propWithSubtypingGetterAndSetter; + // Error ?number ~> number var testPropOverridenWithGetter: number = foo.propOverriddenWithGetter; // Error string ~> number @@ -261,6 +265,7 @@ var testGetterNoError2: number = obj.goodGetterWithAnnotation; var testGetterWithError1: string = obj.goodGetterNoAnnotation; // Error number ~> string var testGetterWithError2: string = obj.goodGetterWithAnnotation; + // Error number ~> string // Test setting properties with getters obj.goodSetterNoAnnotation = 123; @@ -269,13 +274,16 @@ obj.goodSetterWithAnnotation = 123; obj.goodSetterNoAnnotation = \"hello\"; // Error string ~> number obj.goodSetterWithAnnotation = \"hello\"; + // Error string ~> number var testSubtypingGetterAndSetter: number = obj.propWithSubtypingGetterAndSetter; + // Error ?number ~> number // When building this feature, it was tempting to flow the setter into the // getter and then use either the getter or setter as the type of the property. // This example shows the danger of using the getter\'s type obj.exampleOfOrderOfGetterAndSetter = new C(); + // Error C ~> B // And this example shows the danger of using the setter\'s type. var testExampleOrOrderOfGetterAndSetterReordered: number = obj.exampleOfOrderOfGetterAndSetterReordered; // Error A ~> B @@ -402,15 +410,12 @@ class Base { get get(): B { return this.x; } - set set(value: B): void { this.x = value; } - get getset(): B { return this.x; } - set getset(value: B): void { this.x = value; } diff --git a/tests/import_type/__snapshots__/jsfmt.spec.js.snap b/tests/import_type/__snapshots__/jsfmt.spec.js.snap index cb8617a3..054773a6 100644 --- a/tests/import_type/__snapshots__/jsfmt.spec.js.snap +++ b/tests/import_type/__snapshots__/jsfmt.spec.js.snap @@ -133,7 +133,6 @@ export function givesAFoo3Obj(): AliasFoo3 { } }; } - " `; @@ -274,6 +273,7 @@ var a1: ClassFoo1 = foo1Inst; var a2: number = foo1Inst; // Error: ClassFoo1 ~> number new ClassFoo1(); + // Error: ClassFoo1 is not a value-identifier /////////////////////////////////////////////// // == Importing Class Type (Named Export) == // @@ -285,6 +285,7 @@ var b1: ClassFoo2 = foo2Inst; var b2: number = foo2Inst; // Error: ClassFoo2 ~> number new ClassFoo2(); + // Error: ClassFoo2 is not a value-identifier ///////////////////////////////////////////////////// // == Importing Class Type (CJS Default Export) == // @@ -293,6 +294,7 @@ import type ClassFoo3T from \"./ExportCJSDefault_Class\"; import ClassFoo3 from \"./ExportCJSDefault_Class\"; var c1: ClassFoo3T = new ClassFoo3(); new ClassFoo3T(); + // Error: ClassFoo3 is not a value-identifier /////////////////////////////////////////////////// // == Importing Class Type (CJS Named Export) == // @@ -307,6 +309,7 @@ new ClassFoo4(); // Error: ClassFoo4 is not a value-identifier // TODO: this errors correctly, but the message is just \'can\'t resolve name\' var d3: typeof ClassFoo5 = foo5Inst; + // Error: Can\'t typeof a type alias //////////////////////////////////////////// // == Import Type Alias (Named Export) == // @@ -317,6 +320,7 @@ var e1: AliasFoo3 = givesAFoo3Obj(); var e2: number = givesAFoo3Obj(); // Error: AliasFoo3 ~> number var e3: typeof AliasFoo3 = givesAFoo3Obj(); + // Error: Can\'t typeof a type alias ////////////////////////////////////////////// // == Import Type Alias (Default Export) == // @@ -328,6 +332,7 @@ var e3: typeof AliasFoo3 = givesAFoo3Obj(); // == Import Type With Non-Alias Compatible Value == // /////////////////////////////////////////////////////// import type { numValue } from \"./ExportsANumber\"; + // Error: Cannot import-type a number value //////////////////////////////////////////////////////////////////////// // == Regression Test: https://github.com/facebook/flow/issues/359 == // diff --git a/tests/import_typeof/__snapshots__/jsfmt.spec.js.snap b/tests/import_typeof/__snapshots__/jsfmt.spec.js.snap index b688eb5b..39cb6339 100644 --- a/tests/import_typeof/__snapshots__/jsfmt.spec.js.snap +++ b/tests/import_typeof/__snapshots__/jsfmt.spec.js.snap @@ -132,7 +132,6 @@ export function givesAFoo3Obj(): AliasFoo3 { } }; } - " `; @@ -305,6 +304,7 @@ var a1: ClassFoo1T = ClassFoo1; var a2: ClassFoo1T = new ClassFoo1(); // Error: ClassFoo1 (inst) ~> ClassFoo1 (class) new ClassFoo1T(); + // Error: ClassFoo1T is not bound to a value ///////////////////////////////////////////////// // == Importing Class Typeof (Named Export) == // @@ -316,6 +316,7 @@ var b1: ClassFoo2T = ClassFoo2; var b2: ClassFoo2T = new ClassFoo2(); // Error: ClassFoo2 (inst) ~> ClassFoo2 (class) new ClassFoo2T(); + // Error: ClassFoo2T is not bound to a value /////////////////////////////////////////////////////// // == Importing Class Typeof (CJS Default Export) == // @@ -325,6 +326,7 @@ import ClassFoo3 from \"./ExportCJSDefault_Class\"; var c1: ClassFoo3T = ClassFoo3; var c2: ClassFoo3T = new ClassFoo3(); + // Error: ClassFoo3 (inst) ~> ClassFoo3 (class) ///////////////////////////////////////////////////// // == Importing Class Typeof (CJS Named Export) == // @@ -334,11 +336,13 @@ import { ClassFoo4 } from \"./ExportCJSNamed_Class\"; var d1: ClassFoo4T = ClassFoo4; var d2: ClassFoo4T = new ClassFoo4(); + // Error: ClassFoo4 (inst) ~> ClassFoo4 (class) ////////////////////////////////////////////// // == Import Typeof Alias (Named Export) == // ////////////////////////////////////////////// import typeof { AliasFoo3 } from \"./ExportNamed_Alias\"; + // Error: Can\'t \`import typeof\` type aliases! //////////////////////////////////////////////// // == Import Typeof Alias (Default Export) == // @@ -353,6 +357,7 @@ import typeof num_default from \"./ExportDefault_Number\"; var f1: num_default = 42; var f2: num_default = \"asdf\"; + // Error: string ~> number ///////////////////////////////////////////////////////////// // == Import Typeof With Non-Class Value (Named Export) == // @@ -361,6 +366,7 @@ import typeof { num as num_named } from \"./ExportNamed_Number\"; var g1: num_named = 42; var g2: num_named = \"asdf\"; + // Error: string ~> number /////////////////////////////////////////////////////////////////// // == Import Typeof With Non-Class Value (CJS Default Export) == // @@ -369,6 +375,7 @@ import typeof num_cjs_default from \"./ExportCJSDefault_Number\"; var h1: num_cjs_default = 42; var h2: num_cjs_default = \"asdf\"; + // Error: string ~> number ///////////////////////////////////////////////////////////////// // == Import Typeof With Non-Class Value (CJS Named Export) == // @@ -377,6 +384,7 @@ import typeof { num as num_cjs_named } from \"./ExportCJSNamed_Number\"; var i1: num_cjs_named = 42; var i2: num_cjs_named = \"asdf\"; + // Error: string ~> number /////////////////////////////////////////////// // == Import Typeof ModuleNamespaceObject == // diff --git a/tests/instanceof/__snapshots__/jsfmt.spec.js.snap b/tests/instanceof/__snapshots__/jsfmt.spec.js.snap index d32238bb..597e767b 100644 --- a/tests/instanceof/__snapshots__/jsfmt.spec.js.snap +++ b/tests/instanceof/__snapshots__/jsfmt.spec.js.snap @@ -93,7 +93,6 @@ function foo1(x: Array | number) { class X1 { foo: number; } - class X2 { foo: string; } @@ -117,7 +116,6 @@ function consumer2(b) { class Y1 { bar: X1; } - class Y2 { bar: X2; } @@ -141,7 +139,6 @@ function consumer4(b) { class Z1 { baz: Y1; } - class Z2 { baz: Y2; } diff --git a/tests/interface/__snapshots__/jsfmt.spec.js.snap b/tests/interface/__snapshots__/jsfmt.spec.js.snap index 11a81a47..89006f5e 100644 --- a/tests/interface/__snapshots__/jsfmt.spec.js.snap +++ b/tests/interface/__snapshots__/jsfmt.spec.js.snap @@ -54,6 +54,7 @@ var x: string = new C().x; interface I { x: number } var i = new I(); + // error function testInterfaceName(o: I) { (o.name: string); @@ -138,9 +139,12 @@ interface L extends J, K { y: string } function foo(l: L) { l.x; + l.y; + l.z; } + // error: z not found in L // interface + multiple inheritance is similar to object type + intersection type M = { y: string } & J & { z: boolean }; @@ -188,6 +192,7 @@ new C().bar((x: string) => { }); // error, number ~/~> string interface I { foo(x: number): void } (function foo(x: number) { }: I); + // error, property \`foo\` not found function declare class C { bar(i: I): void, bar(f: (x: number) => void): void } diff --git a/tests/intersection/__snapshots__/jsfmt.spec.js.snap b/tests/intersection/__snapshots__/jsfmt.spec.js.snap index c47c90a8..7e3e25e5 100644 --- a/tests/intersection/__snapshots__/jsfmt.spec.js.snap +++ b/tests/intersection/__snapshots__/jsfmt.spec.js.snap @@ -221,6 +221,7 @@ var b: B = a; // intersection of dictionary types: declare var c: C; var d: D = c; + // ok // dict type mismatch type E = { [key: string]: string }; diff --git a/tests/iterable/__snapshots__/jsfmt.spec.js.snap b/tests/iterable/__snapshots__/jsfmt.spec.js.snap index 9f0254d6..c4289206 100644 --- a/tests/iterable/__snapshots__/jsfmt.spec.js.snap +++ b/tests/iterable/__snapshots__/jsfmt.spec.js.snap @@ -194,7 +194,6 @@ function mapTest1(map: Map): Iterable<[string, number]> { function mapTest2(map: Map): Iterable<[K, V]> { return map; } - function mapTest3(map: Map): Iterable<*> { return map; } @@ -230,7 +229,6 @@ function setTest1(set: Set): Iterable { function setTest2(set: Set): Iterable { return set; } - function setTest3(set: Set): Iterable<*> { return set; } @@ -266,6 +264,7 @@ exports[`test variance.js 1`] = ` /* @flow */ (([]: Array): Iterable); + // ok, Iterable<+T> (([]: Array).values(): Iterable); // ok, Iterator<+T> " diff --git a/tests/jsx_intrinsics.builtin/__snapshots__/jsfmt.spec.js.snap b/tests/jsx_intrinsics.builtin/__snapshots__/jsfmt.spec.js.snap index c791e96b..0227c66d 100644 --- a/tests/jsx_intrinsics.builtin/__snapshots__/jsfmt.spec.js.snap +++ b/tests/jsx_intrinsics.builtin/__snapshots__/jsfmt.spec.js.snap @@ -31,6 +31,7 @@ class CustomComponent extends React.Component { var a: React.Element<{ prop: string }> = ; var b: React.Element<{ prop1: string }> = ; + // Error: Props<{prop}> ~> Props<{prop1}> // Since intrinsics are typed as \`any\` out of the box, we can pass any // attributes to intrinsics! @@ -79,10 +80,12 @@ var Str: string = \"str\"; ; /* This is fine*/ ; + // This is fine React.createElement(\"div\", {}); // This is fine React.createElement(\"bad\", {}); + /* This is fine*/
; // This is fine " diff --git a/tests/jsx_intrinsics.custom/__snapshots__/jsfmt.spec.js.snap b/tests/jsx_intrinsics.custom/__snapshots__/jsfmt.spec.js.snap index 5d6966fe..5d61dbe7 100644 --- a/tests/jsx_intrinsics.custom/__snapshots__/jsfmt.spec.js.snap +++ b/tests/jsx_intrinsics.custom/__snapshots__/jsfmt.spec.js.snap @@ -27,6 +27,7 @@ class CustomComponent extends React.Component { var a: React.Element<{ prop: string }> = ; var b: React.Element<{ prop1: string }> = ; + /* Error: Props<{prop}> ~> Props<{prop1}>*/
;
; @@ -71,12 +72,14 @@ var Str: string = \"str\"; ; /* Error: \'bad\' not in JSXIntrinsics*/ ; + // Error: string ~> keys of JSXIntrinsics React.createElement(\"div\", {}); // This is fine React.createElement(\"bad\", {}); // Error: \'bad\' not in JSXIntrinsics React.createElement(Str, {}); + /* Error: string ~> keys of JSXIntrinsics*/ /* TODO: Make this an error*/
; // Not an error but should be eventually diff --git a/tests/keys/__snapshots__/jsfmt.spec.js.snap b/tests/keys/__snapshots__/jsfmt.spec.js.snap index 19fb4e0f..7956bb51 100644 --- a/tests/keys/__snapshots__/jsfmt.spec.js.snap +++ b/tests/keys/__snapshots__/jsfmt.spec.js.snap @@ -54,6 +54,7 @@ function testKeysOfObject(str: string, lit: \"hi\") { (str: $Keys); // No error, truthy string should be fine } (\"hi\": $Keys); + // String literal should be fine (123: $Keys); // Error: number -> keys of Object } @@ -66,6 +67,7 @@ function testKeysOfStrDict(str: string, lit: \"hi\") { (str: $Keys); // No error, truthy string should be fine } (\"hi\": $Keys); + // String literal should be fine (123: $Keys); // Error: number -> keys of StrDict } @@ -80,6 +82,7 @@ function testKeysOfStrLitDict(str: string, lit: \"hi\") { (\"hi\": $Keys); // The right string literal is allowed (\"bye\": $Keys); + // Error: The wrong string literal is not allowed (123: $Keys); // Error: number -> keys of StrLitDict } @@ -92,6 +95,7 @@ function testKeysOfOtherObj(str: string, lit: \"hi\") { (str: $Keys); // Error: truthy string -> keys of ObjLit } (\"hi\": $Keys); + // String literal should be fine (123: $Keys); // Error: number -> keys of ObjLit } diff --git a/tests/last_duplicate_property_wins/__snapshots__/jsfmt.spec.js.snap b/tests/last_duplicate_property_wins/__snapshots__/jsfmt.spec.js.snap index 88d702e6..4ca26348 100644 --- a/tests/last_duplicate_property_wins/__snapshots__/jsfmt.spec.js.snap +++ b/tests/last_duplicate_property_wins/__snapshots__/jsfmt.spec.js.snap @@ -75,6 +75,7 @@ class C { (new C().bar: boolean); // last wins (new C().qux: boolean); + // weird outlier where last doesn\'t win in classes // Objects const o = { diff --git a/tests/literal/__snapshots__/jsfmt.spec.js.snap b/tests/literal/__snapshots__/jsfmt.spec.js.snap index 38f2ef1d..8bb4bcdc 100644 --- a/tests/literal/__snapshots__/jsfmt.spec.js.snap +++ b/tests/literal/__snapshots__/jsfmt.spec.js.snap @@ -41,20 +41,24 @@ function foo(x: $Keys) { } foo(\"AGE\"); foo(\"LOCATION\"); + // error function bar(x: $Keys<{ age: number }>) { } bar(APIKeys.AGE); // not an error: APIKeys.AGE = \"age\" bar(APIKeys.NAME); + // error: since \"NAME\" is not in the smaller enum var object = {}; object[APIKeys.AGE] = 123; // i.e., object.age = 123 object[APIKeys.NAME] = \"FOO\"; + // i.e., object.name = \"FOO\" var age: number = object[APIKeys.AGE]; var name: number = object[APIKeys.NAME]; + // error: object.name is a string var indices = { red: 0, green: 1, blue: 2 }; var tuple = [ 42, \"hello\", false ]; diff --git a/tests/method_properties/__snapshots__/jsfmt.spec.js.snap b/tests/method_properties/__snapshots__/jsfmt.spec.js.snap index 67f22cd8..87127180 100644 --- a/tests/method_properties/__snapshots__/jsfmt.spec.js.snap +++ b/tests/method_properties/__snapshots__/jsfmt.spec.js.snap @@ -53,6 +53,7 @@ C.bar.x; import { Foo } from \"./exports_optional_prop\"; const foo = new Foo(); (foo.bar(): string); + // error, could be undefined function f(x) { (x.bar(): string); // error. caused by \`f(foo)\`; annotate x to track it down. diff --git a/tests/modules/__snapshots__/jsfmt.spec.js.snap b/tests/modules/__snapshots__/jsfmt.spec.js.snap index 2ee71990..c1d475f5 100644 --- a/tests/modules/__snapshots__/jsfmt.spec.js.snap +++ b/tests/modules/__snapshots__/jsfmt.spec.js.snap @@ -48,6 +48,7 @@ function g(x: string) { //function f(x:number) { g(x); return x; } function f(x: number): number { g(x); + return x; } diff --git a/tests/name_prop/__snapshots__/jsfmt.spec.js.snap b/tests/name_prop/__snapshots__/jsfmt.spec.js.snap index 987839ad..5e642311 100644 --- a/tests/name_prop/__snapshots__/jsfmt.spec.js.snap +++ b/tests/name_prop/__snapshots__/jsfmt.spec.js.snap @@ -16,6 +16,7 @@ var test1 = A.bar; // Error bar doesn\'t exist var test2: string = A.name; var test3: number = A.name; + // Error string ~> number var a = new A(); var test4 = a.constructor.bar; diff --git a/tests/node_tests/crypto/__snapshots__/jsfmt.spec.js.snap b/tests/node_tests/crypto/__snapshots__/jsfmt.spec.js.snap index 220c3476..38ed9b0a 100644 --- a/tests/node_tests/crypto/__snapshots__/jsfmt.spec.js.snap +++ b/tests/node_tests/crypto/__snapshots__/jsfmt.spec.js.snap @@ -67,6 +67,7 @@ let tests = [ // 1 error hmac.update(buf); hmac.update(buf, \"utf8\"); + // 1 error: no encoding when passing a buffer // it\'s also chainable (hmac.update(\"some data to hash\").update(buf).digest(): Buffer); diff --git a/tests/node_tests/fs/__snapshots__/jsfmt.spec.js.snap b/tests/node_tests/fs/__snapshots__/jsfmt.spec.js.snap index 9544b4a2..98721eee 100644 --- a/tests/node_tests/fs/__snapshots__/jsfmt.spec.js.snap +++ b/tests/node_tests/fs/__snapshots__/jsfmt.spec.js.snap @@ -55,12 +55,15 @@ fs.readFile(\"file.exp\", {}, (_, data) => { /* readFileSync */ (fs.readFileSync(\"file.exp\"): Buffer); (fs.readFileSync(\"file.exp\"): string); + // error (fs.readFileSync(\"file.exp\", \"blah\"): string); (fs.readFileSync(\"file.exp\", \"blah\"): Buffer); + // error (fs.readFileSync(\"file.exp\", { encoding: \"blah\" }): string); (fs.readFileSync(\"file.exp\", { encoding: \"blah\" }): Buffer); + // error (fs.readFileSync(\"file.exp\", {}): Buffer); (fs.readFileSync(\"file.exp\", {}): string); // error diff --git a/tests/node_tests/json_file/__snapshots__/jsfmt.spec.js.snap b/tests/node_tests/json_file/__snapshots__/jsfmt.spec.js.snap index 15d9748e..826d8d25 100644 --- a/tests/node_tests/json_file/__snapshots__/jsfmt.spec.js.snap +++ b/tests/node_tests/json_file/__snapshots__/jsfmt.spec.js.snap @@ -31,16 +31,20 @@ let data = require(\"./package/index.json\"); (data.foo.bar: void); // error, should be boolean (data.abc: boolean); + // error, should be ?string let data2 = require(\"./package\"); (data2.baz: void); + // error, should be string let data3 = require(\"./package2\"); (data3.foo: void); + // error, should be number (not string! index.js wins) let data4 = require(\"./json_array\"); (data4: Array); (data4: void); + // error, should be Array (require(\"./json_string\"): void); // error, should be string diff --git a/tests/node_tests/os/__snapshots__/jsfmt.spec.js.snap b/tests/node_tests/os/__snapshots__/jsfmt.spec.js.snap index 1af9c5bd..223aaee9 100644 --- a/tests/node_tests/os/__snapshots__/jsfmt.spec.js.snap +++ b/tests/node_tests/os/__snapshots__/jsfmt.spec.js.snap @@ -22,10 +22,12 @@ var os = require(\"os\"); var u1 = os.userInfo(); (u1.username: string); (u1.username: Buffer); + // error var u2 = os.userInfo({ encoding: \"utf8\" }); (u2.username: string); (u2.username: Buffer); + // error var u3 = os.userInfo({ encoding: \"buffer\" }); (u3.username: string); diff --git a/tests/nullable/__snapshots__/jsfmt.spec.js.snap b/tests/nullable/__snapshots__/jsfmt.spec.js.snap index 2faa4567..45ea94a5 100644 --- a/tests/nullable/__snapshots__/jsfmt.spec.js.snap +++ b/tests/nullable/__snapshots__/jsfmt.spec.js.snap @@ -53,6 +53,7 @@ var x = bar(); if (x != null) qux(x); // x: ?string | null if (x != null) corge(x); + // x: ?string | null function grault() { x = null; diff --git a/tests/object-method/__snapshots__/jsfmt.spec.js.snap b/tests/object-method/__snapshots__/jsfmt.spec.js.snap index b7b9868f..96979f29 100644 --- a/tests/object-method/__snapshots__/jsfmt.spec.js.snap +++ b/tests/object-method/__snapshots__/jsfmt.spec.js.snap @@ -121,6 +121,7 @@ function bar(f: () => void) { } bar(foo); + // error, since \`this\` is used non-trivially in \`foo\` function qux(o: { f(): void }) { o.f(); // passing o as \`this\` diff --git a/tests/object_api/__snapshots__/jsfmt.spec.js.snap b/tests/object_api/__snapshots__/jsfmt.spec.js.snap index d5f9db60..b3d7c5b2 100644 --- a/tests/object_api/__snapshots__/jsfmt.spec.js.snap +++ b/tests/object_api/__snapshots__/jsfmt.spec.js.snap @@ -76,6 +76,7 @@ var decl_export_: { foo: any, bar: any } = Object.assign({}, export_); let anyObj: Object = {}; Object.assign(anyObj, anyObj); + // makes sure this terminates module.exports = export_; " @@ -188,6 +189,7 @@ class Bar extends Foo { var sealed = { one: \"one\", two: \"two\" }; (Object.keys(sealed): Array<\"one\" | \"two\">); (Object.keys(sealed): void); + // error, Array var unsealed = {}; Object.keys(unsealed).forEach(k => { @@ -201,6 +203,7 @@ Object.keys(dict).forEach(k => { var any: Object = {}; (Object.keys(any): Array); + // error, Array class Foo { prop: string; @@ -209,6 +212,7 @@ class Foo { } // constructor and foo not enumerable (Object.keys(new Foo()): Array<\"error\">); + // error: prop ~> error class Bar extends Foo { bar_prop: string; @@ -436,6 +440,7 @@ var y = new Foo(); // call takesAString(a.toString()); d.toString(); + // ok, even though dict specifies strings, this is a function // get var aToString: () => string = a.toString; @@ -475,6 +480,7 @@ takesAString(y.toString()); (123).toString(\"foo\"); // error (123).toString(null); + // error // // hasOwnProperty diff --git a/tests/object_assign/__snapshots__/jsfmt.spec.js.snap b/tests/object_assign/__snapshots__/jsfmt.spec.js.snap index af118e2e..19f5fa95 100644 --- a/tests/object_assign/__snapshots__/jsfmt.spec.js.snap +++ b/tests/object_assign/__snapshots__/jsfmt.spec.js.snap @@ -86,6 +86,7 @@ var good: number = A.Good.foo(); var f = A.Bad.foo; // Property access is fine var bad_: number = f(); + // Calling the function is fine var bad: number = A.Bad.foo(); // Method call is not fine /* diff --git a/tests/object_freeze/__snapshots__/jsfmt.spec.js.snap b/tests/object_freeze/__snapshots__/jsfmt.spec.js.snap index 8455ae4d..56afc06d 100644 --- a/tests/object_freeze/__snapshots__/jsfmt.spec.js.snap +++ b/tests/object_freeze/__snapshots__/jsfmt.spec.js.snap @@ -24,8 +24,10 @@ var xx : { x: number } = Object.freeze({ x: \"error\" }) var foo = Object.freeze({ bar: \"12345\" }); foo.bar = \"23456\"; + // error Object.assign(foo, { bar: \"12345\" }); + // error var baz = { baz: 12345 }; var bliffl = Object.freeze({ bar: \"12345\", ...baz }); @@ -39,6 +41,7 @@ bliffl.constructor = baz; // error bliffl.toString = function() { }; + // error baz.baz = 0; diff --git a/tests/objects/__snapshots__/jsfmt.spec.js.snap b/tests/objects/__snapshots__/jsfmt.spec.js.snap index 69c6b6a5..74d07ce1 100644 --- a/tests/objects/__snapshots__/jsfmt.spec.js.snap +++ b/tests/objects/__snapshots__/jsfmt.spec.js.snap @@ -29,6 +29,7 @@ var z = Object(123); // error (next line makes this not match any signatures) (Object(undefined): {}); (Object(void 0): {}); (Object(undefined): Number); + // error var x = Object(null); x.foo = \"bar\"; @@ -82,11 +83,13 @@ x[123] = false; x[\"foo\" + \"bar\"] = \"derp\"; // ok since we can\'t tell (x[\`foo\`]: string); + // error, key doesn\'t exist var y: { foo: string } = { foo: \"bar\" }; y[\"foo\"] = 123; // error, number !~> string y[\"bar\"] = \"abc\"; + // error, property not found (y[\"hasOwnProperty\"]: string); // error, prototype method is not a string " diff --git a/tests/objmap/__snapshots__/jsfmt.spec.js.snap b/tests/objmap/__snapshots__/jsfmt.spec.js.snap index 151d2c9e..8d7169b5 100644 --- a/tests/objmap/__snapshots__/jsfmt.spec.js.snap +++ b/tests/objmap/__snapshots__/jsfmt.spec.js.snap @@ -26,6 +26,7 @@ var o = keyMirror({ FOO: null, BAR: null }); (o.FOO: \"FOO\"); // ok (o.FOO: \"BAR\"); + // error, \'FOO\' incompatible with \'BAR\' promiseAllByKey({ foo: Promise.resolve(0), bar: \"bar\" }).then(o => { (o.foo: string); diff --git a/tests/optional/__snapshots__/jsfmt.spec.js.snap b/tests/optional/__snapshots__/jsfmt.spec.js.snap index bd0ad193..63be1e6a 100644 --- a/tests/optional/__snapshots__/jsfmt.spec.js.snap +++ b/tests/optional/__snapshots__/jsfmt.spec.js.snap @@ -175,6 +175,7 @@ foo(); function qux(x = \"hello\", ...y): string { foo(x); + return y[0]; } @@ -300,6 +301,7 @@ bar(undefined); // ok function foo(x?: number) { } foo(undefined); + // ok function bar(x = \"bar\"): string { return x; @@ -333,6 +335,7 @@ foo(); // OK foo(123), // OK foo(123, \"hello\"); + // OK foo(true); // ERROR boolean ~> number diff --git a/tests/optional_props/__snapshots__/jsfmt.spec.js.snap b/tests/optional_props/__snapshots__/jsfmt.spec.js.snap index 1fa88a8f..4e3e114e 100644 --- a/tests/optional_props/__snapshots__/jsfmt.spec.js.snap +++ b/tests/optional_props/__snapshots__/jsfmt.spec.js.snap @@ -14,6 +14,7 @@ bar({foo: \"\"}); ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ var x: {} = { foo: 0 }; var y: { foo?: string } = x; + // OK in TypeScript, not OK in Flow var z: string = y.foo || \"\"; @@ -21,6 +22,7 @@ var o = {}; y = o; // OK; we know that narrowing could not have happened o.foo = 0; + // future widening is constrained function bar(config: { foo?: number }) { } @@ -48,15 +50,18 @@ var a: { foo?: string } = {}; a.foo = undefined; // This is not an error a.foo = null; + // But this is an error var b: { foo?: ?string } = {}; b.foo = undefined; // This is fine b.foo = null; + // Also fine var c: { foo?: string } = { foo: undefined }; // This is not an error var d: { foo?: string } = { foo: null }; + // But this is an error var e: { foo?: ?string } = { foo: undefined }; // This is fine diff --git a/tests/overload/__snapshots__/jsfmt.spec.js.snap b/tests/overload/__snapshots__/jsfmt.spec.js.snap index d8c31a26..cc90236a 100644 --- a/tests/overload/__snapshots__/jsfmt.spec.js.snap +++ b/tests/overload/__snapshots__/jsfmt.spec.js.snap @@ -76,12 +76,14 @@ a.foo(0); a.foo(\"hey\"); // ok a.foo(true); + // error, function cannot be called on intersection type a.bar({ a: 0 }); // ok a.bar({ a: \"hey\" }); // ok a.bar({ a: true }); + // error, function cannot be called on intersection type declare var x: { a: boolean } & { b: string }; @@ -168,6 +170,7 @@ declare function f(x: string): void; declare function f(x: number): void; declare var x_f: string | number; f(x_f); + // ok // maybe declare function g(x: null): void; @@ -175,6 +178,7 @@ declare function g(x: void): void; declare function g(x: string): void; declare var x_g: ?string; g(x_g); + // ok // optional declare function h(x: void): void; diff --git a/tests/parse_error_haste/__snapshots__/jsfmt.spec.js.snap b/tests/parse_error_haste/__snapshots__/jsfmt.spec.js.snap index 535454ae..a28a3e1e 100644 --- a/tests/parse_error_haste/__snapshots__/jsfmt.spec.js.snap +++ b/tests/parse_error_haste/__snapshots__/jsfmt.spec.js.snap @@ -21,6 +21,7 @@ var C = require(\"./ParseError\"); // Flow file var A = require(\"Foo\"); // non-Flow file @providesModule Foo var B = require(\"./NoProvides\"); + // non-Flow file var C = require(\"./ParseError\"); // Flow file " diff --git a/tests/parse_error_node/__snapshots__/jsfmt.spec.js.snap b/tests/parse_error_node/__snapshots__/jsfmt.spec.js.snap index 80688245..1c3df92d 100644 --- a/tests/parse_error_node/__snapshots__/jsfmt.spec.js.snap +++ b/tests/parse_error_node/__snapshots__/jsfmt.spec.js.snap @@ -18,6 +18,7 @@ var B = require(\"./ParseError\"); // Flow file // non-flow files should not give parse errors var A = require(\"./Imported\"); + // non-Flow file @providesModule Foo var B = require(\"./ParseError\"); // Flow file " diff --git a/tests/poly/__snapshots__/jsfmt.spec.js.snap b/tests/poly/__snapshots__/jsfmt.spec.js.snap index c543e718..28d8578d 100644 --- a/tests/poly/__snapshots__/jsfmt.spec.js.snap +++ b/tests/poly/__snapshots__/jsfmt.spec.js.snap @@ -15,6 +15,7 @@ class A {} new A(); // OK, implicitly inferred type args class B extends A {} + // OK, same as above function foo(b): A { // ok but unsafe, caller may assume any type arg diff --git a/tests/promises/__snapshots__/jsfmt.spec.js.snap b/tests/promises/__snapshots__/jsfmt.spec.js.snap index 7bd62309..5d9f7cfd 100644 --- a/tests/promises/__snapshots__/jsfmt.spec.js.snap +++ b/tests/promises/__snapshots__/jsfmt.spec.js.snap @@ -57,6 +57,7 @@ Promise.all([ (b: boolean); // Error: number ~> boolean (c: string); + // Error: boolean ~> string // array element type is (string | number | boolean) xs.forEach(x => { @@ -66,9 +67,11 @@ Promise.all([ // First argument is required Promise.all(); + // Error: expected array instead of undefined (too few arguments) // Mis-typed arg Promise.all(0); + // Error: expected array instead of number // Promise.all is a function (Promise.all: Function); @@ -694,6 +697,7 @@ exports[`test resolve_void.js 1`] = ` // @flow (Promise.resolve(): Promise); + // error (Promise.resolve(undefined): Promise); // error " diff --git a/tests/react_functional/__snapshots__/jsfmt.spec.js.snap b/tests/react_functional/__snapshots__/jsfmt.spec.js.snap index cb87e3c6..f0f25c99 100644 --- a/tests/react_functional/__snapshots__/jsfmt.spec.js.snap +++ b/tests/react_functional/__snapshots__/jsfmt.spec.js.snap @@ -22,11 +22,13 @@ function F(props: { foo: string }) { ; /* error: number ~> string*/ ; + // ok // props subtyping is property-wise covariant function G(props: { foo: string | numner }) { } ; + // ok var Z = 0; ; // error, expected React component diff --git a/tests/rec/__snapshots__/jsfmt.spec.js.snap b/tests/rec/__snapshots__/jsfmt.spec.js.snap index 997f7848..21c2f54a 100644 --- a/tests/rec/__snapshots__/jsfmt.spec.js.snap +++ b/tests/rec/__snapshots__/jsfmt.spec.js.snap @@ -92,11 +92,14 @@ pstar = (new P: P>); // OK class P { x: X; } + // this is like Promise type Pstar = X | Pstar>; + // this is like Promise* var p: P = new P(); (p.x: string); + // error var pstar: Pstar = 0; // OK @@ -106,6 +109,7 @@ var pstar: Pstar = 0; pstar = p; // OK (pstar.x: string); + // error pstar = (new P(): P>); // OK diff --git a/tests/record/__snapshots__/jsfmt.spec.js.snap b/tests/record/__snapshots__/jsfmt.spec.js.snap index 79269801..2caf84cb 100644 --- a/tests/record/__snapshots__/jsfmt.spec.js.snap +++ b/tests/record/__snapshots__/jsfmt.spec.js.snap @@ -36,6 +36,7 @@ o1.foo; o1.qux; // error: qux not found o1.toString(); + // ok type R = { foo: any, bar: any }; type Key2 = $Keys; @@ -45,6 +46,7 @@ var o2: { [key: Key2]: number } = { foo: 0 }; o2.bar; // OK to access bar o2.qux; + // error: qux not found class C { x: $Subtype<{ [key: $Keys]: any }>; // object with larger key set than X\'s diff --git a/tests/refinements/__snapshots__/jsfmt.spec.js.snap b/tests/refinements/__snapshots__/jsfmt.spec.js.snap index 6d4bbd66..49eddc5a 100644 --- a/tests/refinements/__snapshots__/jsfmt.spec.js.snap +++ b/tests/refinements/__snapshots__/jsfmt.spec.js.snap @@ -2213,7 +2213,6 @@ function corge(text: string | number | Array): string { // should only error for string since Array was filtered out. \"number\": return text++ + \"\"; - default: return \"wat\"; } diff --git a/tests/require/__snapshots__/jsfmt.spec.js.snap b/tests/require/__snapshots__/jsfmt.spec.js.snap index 2ce6c59a..16884aaa 100644 --- a/tests/require/__snapshots__/jsfmt.spec.js.snap +++ b/tests/require/__snapshots__/jsfmt.spec.js.snap @@ -157,6 +157,7 @@ require(\"./D\"); var E = require(\"./E\"); var e_1: number = E.numberValue; E.stringValue; + // Error: The E exports obj has no \'stringValue\' property // We require that the param passed to require() be a string literal to support // guaranteed static extraction @@ -166,6 +167,7 @@ require(a); require(\`./E\`); // template literals are ok... require(\`\${\"./E\"}\`); + // error: but only if they have no expressions // require.call is allowed but circumverts Flow\'s static analysis require.call(null, \"DoesNotExist\"); diff --git a/tests/requireLazy/__snapshots__/jsfmt.spec.js.snap b/tests/requireLazy/__snapshots__/jsfmt.spec.js.snap index 83a0c27d..8a416de8 100644 --- a/tests/requireLazy/__snapshots__/jsfmt.spec.js.snap +++ b/tests/requireLazy/__snapshots__/jsfmt.spec.js.snap @@ -72,6 +72,7 @@ requireLazy([ \"A\", \"B\" ], function(A, B) { var num2: number = A.stringValueA; // Error: string ~> number var str2: string = A.numberValueA; + // Error: number ~> string var num3: number = B.numberValueB; var str3: string = B.stringValueB; diff --git a/tests/return_new/__snapshots__/jsfmt.spec.js.snap b/tests/return_new/__snapshots__/jsfmt.spec.js.snap index 98cb0e0f..310d33ba 100644 --- a/tests/return_new/__snapshots__/jsfmt.spec.js.snap +++ b/tests/return_new/__snapshots__/jsfmt.spec.js.snap @@ -16,15 +16,18 @@ function Foo() { return {}; } var foo: number = new Foo(); + // error (returns object literal above) function Bar() { return 0; } var bar: number = new Bar(); + // error (returns new object) function Qux() { } var qux: number = new Qux(); + // error (returns new object) class A {} function B() { @@ -55,8 +58,10 @@ declare class D { var d = new D(); d.x = \"\"; + // error, string ~/~ number (but property x is found) (new D(): D); + // error, new D is an object, D not in proto chain module.exports = D; " diff --git a/tests/sealed/__snapshots__/jsfmt.spec.js.snap b/tests/sealed/__snapshots__/jsfmt.spec.js.snap index d098debd..77293458 100644 --- a/tests/sealed/__snapshots__/jsfmt.spec.js.snap +++ b/tests/sealed/__snapshots__/jsfmt.spec.js.snap @@ -60,6 +60,7 @@ Foo.prototype = { }; var export_o: { x: any } = o; + // awkward type cast module.exports = export_o; " diff --git a/tests/sealed_objects/__snapshots__/jsfmt.spec.js.snap b/tests/sealed_objects/__snapshots__/jsfmt.spec.js.snap index 98ca4766..596e5a50 100644 --- a/tests/sealed_objects/__snapshots__/jsfmt.spec.js.snap +++ b/tests/sealed_objects/__snapshots__/jsfmt.spec.js.snap @@ -21,21 +21,27 @@ var o7: { x: number; y?: string; } = ({ x: 0, y: 0 }: { x: number; [_:any]:numbe ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ var o1 = { x: 0 }; var s1: string = o1.y; + // error var o2: { x: number, y?: string } = { x: 0 }; var s2: string = o2.y || \"\"; + // ok var o3: { x: number, y?: string } = ({ x: 0, y: 0 }: { x: number }); var s3: string = o3.y || \"\"; + // error var o4: { x: number, y?: string } = ({ x: 0 }: { [_: any]: any, x: number }); var s4: string = o4.y || \"\"; + // ok var o5 = { x: 0, ...{} }; var s5: string = o5.y; + // ok (spreads make object types extensible) var o6: { [_: any]: any, x: number } = { x: 0 }; var s6: string = o6.y; + // ok (indexers make object types extensible) var o7: { x: number, y?: string } = ({ x: 0, y: 0 }: { [_: any]: number, diff --git a/tests/simple_arrays/__snapshots__/jsfmt.spec.js.snap b/tests/simple_arrays/__snapshots__/jsfmt.spec.js.snap index 917b5196..7ba4207f 100644 --- a/tests/simple_arrays/__snapshots__/jsfmt.spec.js.snap +++ b/tests/simple_arrays/__snapshots__/jsfmt.spec.js.snap @@ -28,7 +28,6 @@ for (var i = 0; i < 10; ++i) { } else { a[i] = \"\"; } - } // \`i\` never gets a lower bound, so the array access is stalled until the @@ -71,7 +70,6 @@ for (var i = 0; i < 10; ++i) { } else { a[i] = \"\"; } - } function foo(i: number): string { diff --git a/tests/singleton/__snapshots__/jsfmt.spec.js.snap b/tests/singleton/__snapshots__/jsfmt.spec.js.snap index 607a779c..bbbecd9d 100644 --- a/tests/singleton/__snapshots__/jsfmt.spec.js.snap +++ b/tests/singleton/__snapshots__/jsfmt.spec.js.snap @@ -45,6 +45,7 @@ function veryOptimistic(isThisAwesome: true): boolean { var x: boolean = veryOptimistic(true); var y: boolean = veryOptimistic(false); + // error function veryPessimistic(isThisAwesome: true): boolean { return !isThisAwesome; // test bool conversion @@ -52,6 +53,7 @@ function veryPessimistic(isThisAwesome: true): boolean { var x: boolean = veryPessimistic(true); var y: boolean = veryPessimistic(false); + // error type MyOwnBooleanLOL = true | false; @@ -66,6 +68,7 @@ function bar(x: MyOwnBooleanLOL): false { bar(true); bar(false); bar(1); + // error function alwaysFalsy(x: boolean): false { if (x) { @@ -110,6 +113,7 @@ function highlander(howMany: 1): number { highlander(1); highlander(2); + // error type Foo = 1 | 2; @@ -120,6 +124,7 @@ function bar(num: Foo): number { bar(1); bar(2); bar(3); + // error type ComparatorResult = -1 | 0 | 1; function sort(fn: (x: any, y: any) => ComparatorResult) { diff --git a/tests/structural_subtyping/__snapshots__/jsfmt.spec.js.snap b/tests/structural_subtyping/__snapshots__/jsfmt.spec.js.snap index 25719321..5619483b 100644 --- a/tests/structural_subtyping/__snapshots__/jsfmt.spec.js.snap +++ b/tests/structural_subtyping/__snapshots__/jsfmt.spec.js.snap @@ -138,6 +138,7 @@ interface HasOptional { a: string, b?: number } var test1: HasOptional = { a: \"hello\" }; var test2: HasOptional = {}; + // Error: missing property a var test3: HasOptional = { a: \"hello\", b: true }; // Error: boolean ~> number " diff --git a/tests/suppress/__snapshots__/jsfmt.spec.js.snap b/tests/suppress/__snapshots__/jsfmt.spec.js.snap index 7e9749d1..02557f74 100644 --- a/tests/suppress/__snapshots__/jsfmt.spec.js.snap +++ b/tests/suppress/__snapshots__/jsfmt.spec.js.snap @@ -26,9 +26,11 @@ var test6: string = 123; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // $FlowFixMe var test1: string = 123; + // This error should be suppressed // $FlowIssue var test2: string = 123; + // This error should be suppressed function getNum() { return 123; @@ -36,12 +38,15 @@ function getNum() { // $FlowFixMe This was the second loc in the error var test3: string = getNum(); + // This error should be suppressed // $FlowFixMe Error unused suppression var test4: string = 123; + // This error is NOT suppressed // $FlowFixMe Indentation shouldn\'t matter var test5: string = 123; + // This error should be suppressed /* * $FlowNewLine diff --git a/tests/switch/__snapshots__/jsfmt.spec.js.snap b/tests/switch/__snapshots__/jsfmt.spec.js.snap index b8c4ae95..60b9dc0f 100644 --- a/tests/switch/__snapshots__/jsfmt.spec.js.snap +++ b/tests/switch/__snapshots__/jsfmt.spec.js.snap @@ -193,6 +193,7 @@ function foo(x: mixed): string { (a: string); // error, string | number ~/> string (a: number); + // error, string | number ~/> number // b is now number (b: number); @@ -218,11 +219,13 @@ function baz(x: mixed): number { (a: string); // error, string | number ~/> string (a: number); + // error, string | number ~/> number // b is now string | number (b: string); // error, string | number ~/> string (b: number); + // error, string | number ~/> number return a + b; // error, string ~/> number } diff --git a/tests/taint/__snapshots__/jsfmt.spec.js.snap b/tests/taint/__snapshots__/jsfmt.spec.js.snap index fe9b88e6..7f406a34 100644 --- a/tests/taint/__snapshots__/jsfmt.spec.js.snap +++ b/tests/taint/__snapshots__/jsfmt.spec.js.snap @@ -111,6 +111,7 @@ let tests = [ function(x: $Tainted) { let obj: Object = {}; obj.foo(x); + // error, taint ~> any let foo = obj.foo; foo(x); // error, taint ~> any diff --git a/tests/template/__snapshots__/jsfmt.spec.js.snap b/tests/template/__snapshots__/jsfmt.spec.js.snap index 19e3cc21..8025ccee 100644 --- a/tests/template/__snapshots__/jsfmt.spec.js.snap +++ b/tests/template/__snapshots__/jsfmt.spec.js.snap @@ -70,10 +70,12 @@ let tests = [ (\`bar\`: \"bar\"); // ok (\`baz\`: number); + // error \`foo \${123} bar\`; // ok, number can be appended to string \`foo \${{ bar: 123 }} baz\`; + // error, object can\'t be appended let tests = [ function(x: string) { diff --git a/tests/this/__snapshots__/jsfmt.spec.js.snap b/tests/this/__snapshots__/jsfmt.spec.js.snap index 04d4672f..3aa411bb 100644 --- a/tests/this/__snapshots__/jsfmt.spec.js.snap +++ b/tests/this/__snapshots__/jsfmt.spec.js.snap @@ -76,11 +76,13 @@ var o1 = new F(); // sets o1.x to 0 o1.x = \"\"; foo(o1.x); + // ok by definite assignment var o2 = new F(); o1.y = 0; o2.y = \"\"; foo(o2.y); + // setting o1.y to 0 has no effect on o2.y var o3 = new F(); o3.m(); @@ -89,6 +91,7 @@ o3.y = \"\"; foo(o3.y); // ok by definite assignment foo(o2.y); + // setting o3.y to 0 has no effect on o2.y /* * this bindings: @@ -106,6 +109,7 @@ var f1_3 = f1.bind({ x: \"\" })(); // error, string -> number // TODO make this error blame the call site, rather than the function body var f1_4 = f1(); + // error, (global object).x /* arrow functions bind this at point of definition */ /* top level arrow functions bind this to global object */ @@ -114,6 +118,7 @@ var a1 = () => { }; var ax = a1(); + // error, (this:mixed).x /* nested arrows bind enclosing this (which may itself rebind) */ function f2(): number { @@ -131,6 +136,7 @@ var f2_3 = f2.bind({ x: \"\" })(); // error, string -> number // TODO make this error blame the call site, rather than the function body var f2_4 = f2(); + // error, (global object).x (this: void); @@ -182,6 +188,7 @@ var f = c.foo(); var i = f(); // OK (i: C); + // OK class D extends C {} var d = new D(); @@ -189,6 +196,7 @@ var g = d.foo(); var j = g(); // OK (j: D); + // error, since return type of bar is C, not the type of \`this\` class E { foo(x: number) { diff --git a/tests/this_type/__snapshots__/jsfmt.spec.js.snap b/tests/this_type/__snapshots__/jsfmt.spec.js.snap index e8ebc8dd..17d2d646 100644 --- a/tests/this_type/__snapshots__/jsfmt.spec.js.snap +++ b/tests/this_type/__snapshots__/jsfmt.spec.js.snap @@ -87,6 +87,7 @@ class D extends C {} var d = new D(); (d: C).next = new C(); (d.next: D); + // sneaky class A { foo(that: X) { @@ -249,6 +250,7 @@ class B1 extends A1 { } (new B1().bar(): B1); + // OK class B3 extends A3 { foo(): B3 { @@ -259,6 +261,7 @@ class B3 extends A3 { (new B3().bar(): B3<*>); // OK (new B3().qux(0): string); + // error (new B3().bar(): A2<*>); // OK @@ -377,6 +380,7 @@ class A { } } class B extends A {} + // inherits statics method too, with \`this\` bound to the class (A.make(): A); // OK @@ -488,6 +492,7 @@ class Override extends Base { qux() { return this; } + // OK, too bar() { return new Override(); @@ -540,6 +545,7 @@ class Override2 extends Base2 { qux(): this { return this; } + // OK, too bar(): Override2 { return new Override2(); @@ -566,6 +572,7 @@ class InheritOverride2 extends Override2 {} ((new Override2(): Base2).foo(): Base2); (new InheritOverride2().bar_caller(): InheritOverride2); + // exploits error above (new Override2(): Base2).corge(new Base2()); // exploits error above " diff --git a/tests/tuples/__snapshots__/jsfmt.spec.js.snap b/tests/tuples/__snapshots__/jsfmt.spec.js.snap index c9adebad..43f37ef5 100644 --- a/tests/tuples/__snapshots__/jsfmt.spec.js.snap +++ b/tests/tuples/__snapshots__/jsfmt.spec.js.snap @@ -34,6 +34,7 @@ exports[`test optional.js 1`] = ` ([ 0, undefined ]: [number, ?string]); // Ok, correct arity ([ 0 ]: [number, ?string]); + // Error, arity is enforced ([]: [?number, string]); // error, since second element is not marked optional " diff --git a/tests/type_args_nonstrict/__snapshots__/jsfmt.spec.js.snap b/tests/type_args_nonstrict/__snapshots__/jsfmt.spec.js.snap index df38a757..0be9b150 100644 --- a/tests/type_args_nonstrict/__snapshots__/jsfmt.spec.js.snap +++ b/tests/type_args_nonstrict/__snapshots__/jsfmt.spec.js.snap @@ -94,6 +94,7 @@ class MyClass { } var c: MyClass = new MyClass(0); + // no error // no arity error in type annotation using polymorphic class with defaulting class MyClass2 { @@ -106,14 +107,17 @@ class MyClass2 { } var c2: MyClass2 = new MyClass2(0, \"\"); + // no error // no arity error in type annotation using polymorphic type alias type MyObject = { x: T }; var o: MyObject = { x: 0 }; + // no error // arity error in type alias rhs type MySubobject = { y: number } & MyObject; + // no error // arity error in interface extends interface MyInterface { x: T } diff --git a/tests/type_args_strict/__snapshots__/jsfmt.spec.js.snap b/tests/type_args_strict/__snapshots__/jsfmt.spec.js.snap index 71ea4169..73644bdc 100644 --- a/tests/type_args_strict/__snapshots__/jsfmt.spec.js.snap +++ b/tests/type_args_strict/__snapshots__/jsfmt.spec.js.snap @@ -92,6 +92,7 @@ class MyClass { } var c: MyClass = new MyClass(0); + // error, missing argument list (1) // arity error in type annotation using polymorphic class with defaulting class MyClass2 { @@ -104,14 +105,17 @@ class MyClass2 { } var c2: MyClass2 = new MyClass2(0, \"\"); + // error, missing argument list (1-2) // arity error in type annotation using polymorphic type alias type MyObject = { x: T }; var o: MyObject = { x: 0 }; + // error, missing argument list // arity error in type alias rhs type MySubobject = { y: number } & MyObject; + // error, missing argument list // arity error in interface extends interface MyInterface { x: T } diff --git a/tests/type_param_defaults/__snapshots__/jsfmt.spec.js.snap b/tests/type_param_defaults/__snapshots__/jsfmt.spec.js.snap index ccde958b..8bf65153 100644 --- a/tests/type_param_defaults/__snapshots__/jsfmt.spec.js.snap +++ b/tests/type_param_defaults/__snapshots__/jsfmt.spec.js.snap @@ -88,8 +88,10 @@ var b_star: B<*> = new B(123); (b_void.p: boolean); // Error void ~> boolean (b_default.p: boolean); + // Error string ~> boolean (b_star.p: boolean); + // Error number ~> boolean class C extends A {} @@ -104,6 +106,7 @@ var c_star: C<*> = new C(\"hello\"); (c_default.p: boolean); // Error string ~> boolean (c_star.p: boolean); + // Error string ~> boolean class D extends A {} var d_number: D = new D(123); @@ -114,6 +117,7 @@ var d_too_few_args: D<> = new D(\"hello\"); var d_too_many: D = new D(\"hello\"); // Error too many tparams var d_star: D<*> = new D(10); + // error, number ~> string (d_number.p: boolean); // Error number ~> boolean @@ -122,18 +126,22 @@ var d_star: D<*> = new D(10); (d_default.p: boolean); // Error string ~> boolean (d_star.p: boolean); + // Error number ~> boolean class E {} // Error: string ~> number class F {} + // Error: number ~> string class G extends A {} var g_default: G = new G(\"hello\"); (g_default.p: boolean); + // Error string ~> boolean class H {} + // Error - can\'t refer to T before it\'s defined class I extends A {} diff --git a/tests/type_param_scope/__snapshots__/jsfmt.spec.js.snap b/tests/type_param_scope/__snapshots__/jsfmt.spec.js.snap index 601f64ca..100d8496 100644 --- a/tests/type_param_scope/__snapshots__/jsfmt.spec.js.snap +++ b/tests/type_param_scope/__snapshots__/jsfmt.spec.js.snap @@ -155,6 +155,7 @@ g.m(0); g.m(true); // err, bool ~> number|string (g.m(\"\"): G); + // err, string ~> number // Shadow bounds incompatible with parent class H { diff --git a/tests/typeof/__snapshots__/jsfmt.spec.js.snap b/tests/typeof/__snapshots__/jsfmt.spec.js.snap index f42a1449..34fd20af 100644 --- a/tests/typeof/__snapshots__/jsfmt.spec.js.snap +++ b/tests/typeof/__snapshots__/jsfmt.spec.js.snap @@ -144,6 +144,7 @@ var c: typeof MyClass2 = new MyClass2(); var numValue: number = 42; var d: typeof numValue = 100; var e: typeof numValue = \"asdf\"; + // Error: string ~> number ///////////////////////////////// // == typeof <> == // @@ -155,6 +156,7 @@ type numberAlias = number; // is suboptimal - just \'cannot resolve name\'. TODO. // var f: typeof numberAlias = 42; + // Error: \'typeof <>\' makes no sense... /** * Use of a non-class/non-function value in type annotation. diff --git a/tests/unchecked_node_module_vs_lib/__snapshots__/jsfmt.spec.js.snap b/tests/unchecked_node_module_vs_lib/__snapshots__/jsfmt.spec.js.snap index a4db3f0f..c1013144 100644 --- a/tests/unchecked_node_module_vs_lib/__snapshots__/jsfmt.spec.js.snap +++ b/tests/unchecked_node_module_vs_lib/__snapshots__/jsfmt.spec.js.snap @@ -38,17 +38,20 @@ var x3: string = buffer3.INSPECT_MAX_BYTES; // error, module not found // var buffer = require(\"buffer\"); var b: boolean = buffer.INSPECT_MAX_BYTES; + // error, number ~/> boolean // node_modules/crypto/index.js is checked, // so we should pick up its boolean redefinition of DEFAULT_ENCODING // var crypto = require(\"crypto\"); var b: boolean = crypto.DEFAULT_ENCODING; + // no error, we\'ve overridden // names that are explicit paths shouldn\'t fall back to lib defs // var buffer2 = require(\"./buffer\"); var x2: string = buffer2.INSPECT_MAX_BYTES; + // error, module not found var buffer3 = require(\"./buffer.js\"); var x3: string = buffer3.INSPECT_MAX_BYTES; // error, module not found diff --git a/tests/undefined/__snapshots__/jsfmt.spec.js.snap b/tests/undefined/__snapshots__/jsfmt.spec.js.snap index 227f852b..0fd84960 100644 --- a/tests/undefined/__snapshots__/jsfmt.spec.js.snap +++ b/tests/undefined/__snapshots__/jsfmt.spec.js.snap @@ -15,6 +15,7 @@ foo(); function doSomethingAsync(): Promise { return new Promise((resolve, reject) => { resolve(); + // OK to leave out arg, same as resolve(undefined) var anotherVoidPromise: Promise = Promise.resolve(); resolve(anotherVoidPromise); @@ -96,6 +97,7 @@ let tests = [ var id; var name = id ? \"John\" : undefined; (name: boolean); + // error, string or void const bar = [ undefined, \"bar\" ]; (bar[x]: boolean); // error, string or void @@ -103,6 +105,7 @@ let tests = [ function(x: number) { var undefined = \"foo\"; (undefined: string); + // ok var x; if (x !== undefined) { diff --git a/tests/union/__snapshots__/jsfmt.spec.js.snap b/tests/union/__snapshots__/jsfmt.spec.js.snap index f79a666a..17476359 100644 --- a/tests/union/__snapshots__/jsfmt.spec.js.snap +++ b/tests/union/__snapshots__/jsfmt.spec.js.snap @@ -168,7 +168,6 @@ foostr = barstr; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ /* @flow */ class Foo {} - class Bar {} var foostr: Foo | string = new Foo(); @@ -352,6 +351,7 @@ foo(y); // TODO: spurious error! (replacing C with number makes the error go away) // type Bar = (() => C) | (() => string); type Bar = () => C | string; + // workaround function f() { return \"\"; diff --git a/tests/union_new/__snapshots__/jsfmt.spec.js.snap b/tests/union_new/__snapshots__/jsfmt.spec.js.snap index 4e04d09e..88cd6def 100644 --- a/tests/union_new/__snapshots__/jsfmt.spec.js.snap +++ b/tests/union_new/__snapshots__/jsfmt.spec.js.snap @@ -24,11 +24,9 @@ class VirtualNode { /* @flow */ type T = A | B; class U {} - declare var children: U; (children: T | U); class A {} - class B {} type VirtualElement = Thunk | VirtualNode; @@ -457,6 +455,7 @@ function obj(a: A1 | A2) { } const obj_result = obj({ x: \"\" }); + // currently an error! (expect it to be OK) // Type definitions used above are defined below, but in an order that // deliberately makes their full resolution as lazy as possible. The call above @@ -1280,6 +1279,7 @@ length({ kind: \"cons\" }); // missing \`next\` length({ kind: \"cons\", next: { kind: \"nil\" } }); length({ kind: \"empty\" }); + // \`kind\` not found type List = Nil | Cons; type Nil = { kind: \"nil\" };