newtests/autocomplete/test.js (854 lines of code) (raw):
/*
* @flow
*/
import type {Suite} from "flow-dev-tools/src/test/Suite";
const {suite, test} = require('flow-dev-tools/src/test/Tester');
module.exports = (suite(({addFile, flowCmd}) => [
test('non-json output', [
addFile('foo_parse_fail.js'),
flowCmd(
['autocomplete', '--strip-root', 'foo_parse_fail.js', '10', '17'],
'foo_parse_fail.js',
).stdout(
`
hasOwnProperty (prop: mixed) => boolean
isPrototypeOf (o: mixed) => boolean
num number
propertyIsEnumerable (prop: mixed) => boolean
str string
toLocaleString () => string
toString () => string
valueOf () => mixed
`,
).exitCodes([0]),
]),
test("json output", [
addFile("foo.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'foo.js', '10', '5'],
'foo.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "num",
"type": "number"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "str",
"type": "string"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("bar.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'bar.js', '4', '5'],
'bar.js',
).stdout(
`{
"error": "not enough type information to extract members",
"result": []
}`,
).exitCodes([0]),
addFile("qux.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'qux.js', '6', '3'],
'qux.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
},
{
"name": "x",
"type": "number"
}
]
}
`,
).exitCodes([0]),
addFile("str.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'str.js', '3', '9'],
'str.js',
).stdout(
`
{
"result": [
{
"name": "[Symbol.iterator]",
"type": "() => Iterator<string>"
},
{
"name": "anchor",
"type": "(name: string) => string"
},
{
"name": "charAt",
"type": "(pos: number) => string"
},
{
"name": "charCodeAt",
"type": "(index: number) => number"
},
{
"name": "codePointAt",
"type": "(index: number) => number"
},
{
"name": "concat",
"type": "(...strings: Array<string>) => string"
},
{
"name": "endsWith",
"type": "(searchString: string, position?: number) => boolean"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "includes",
"type": "(searchString: string, position?: number) => boolean"
},
{
"name": "indexOf",
"type": "(searchString: string, position?: number) => number"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "lastIndexOf",
"type": "(searchString: string, position?: number) => number"
},
{
"name": "length",
"type": "number"
},
{
"name": "link",
"type": "(href: string) => string"
},
{
"name": "localeCompare",
"type": "(that: string, locales?: (string | Array<string>), options?: Intl$CollatorOptions) => number"
},
{
"name": "match",
"type": "(regexp: (string | RegExp)) => (RegExp$matchResult | null)"
},
{
"name": "matchAll",
"type": "(regexp: (string | RegExp)) => Iterator<RegExp$matchResult>"
},
{
"name": "normalize",
"type": "(format?: string) => string"
},
{
"name": "padEnd",
"type": "(targetLength: number, padString?: string) => string"
},
{
"name": "padStart",
"type": "(targetLength: number, padString?: string) => string"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "repeat",
"type": "(count: number) => string"
},
{
"name": "replace",
"type": "(searchValue: (string | RegExp), replaceValue: (string | ((substring: string, ...args: Array<any>) => string))) => string"
},
{
"name": "search",
"type": "(regexp: (string | RegExp)) => number"
},
{
"name": "slice",
"type": "(start?: number, end?: number) => string"
},
{
"name": "split",
"type": "(separator?: (string | RegExp), limit?: number) => Array<string>"
},
{
"name": "startsWith",
"type": "(searchString: string, position?: number) => boolean"
},
{
"name": "substr",
"type": "(from: number, length?: number) => string"
},
{
"name": "substring",
"type": "(start: number, end?: number) => string"
},
{
"name": "toLocaleLowerCase",
"type": "(locale?: (string | Array<string>)) => string"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toLocaleUpperCase",
"type": "(locale?: (string | Array<string>)) => string"
},
{
"name": "toLowerCase",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "toUpperCase",
"type": "() => string"
},
{
"name": "trim",
"type": "() => string"
},
{
"name": "trimEnd",
"type": "() => string"
},
{
"name": "trimLeft",
"type": "() => string"
},
{
"name": "trimRight",
"type": "() => string"
},
{
"name": "trimStart",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => string"
}
]
}
`,
).exitCodes([0]),
addFile("num.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'num.js', '4', '5'],
'num.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toExponential",
"type": "(fractionDigits?: number) => string"
},
{
"name": "toFixed",
"type": "(fractionDigits?: number) => string"
},
{
"name": "toLocaleString",
"type": "(locales?: (string | Array<string>), options?: Intl$NumberFormatOptions) => string"
},
{
"name": "toPrecision",
"type": "(precision?: number) => string"
},
{
"name": "toString",
"type": "(radix?: number) => string"
},
{
"name": "valueOf",
"type": "() => number"
}
]
}
`,
).exitCodes([0]),
addFile("bool.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'bool.js', '3', '6'],
'bool.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => boolean"
}
]
}
`,
).exitCodes([0]),
addFile("union.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'union.js', '10', '5'],
'union.js',
).stdout(
`
{
"result": [
{
"name": "bar",
"type": "string | any"
},
{
"name": "hasOwnProperty",
"type": "((prop: mixed) => boolean) | any"
},
{
"name": "isPrototypeOf",
"type": "((o: mixed) => boolean) | any"
},
{
"name": "propertyIsEnumerable",
"type": "((prop: mixed) => boolean) | any"
},
{
"name": "toLocaleString",
"type": "(() => string) | any"
},
{
"name": "toString",
"type": "(() => string) | any"
},
{
"name": "valueOf",
"type": "(() => mixed) | any"
}
]
}
`,
).exitCodes([0]),
addFile("object_builtins.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'object_builtins.js', '4', '5'],
'object_builtins.js',
).stdout(
`
{
"error": "not enough type information to extract members",
"result": []
}
`,
).exitCodes([0]),
addFile("function_builtins.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'function_builtins.js', '4', '5'],
'function_builtins.js',
).stdout(
`
{
"error": "not enough type information to extract members",
"result": []
}
`,
).exitCodes([0]),
addFile("fun.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'fun.js', '4', '5'],
'fun.js',
).stdout(
`
{
"result": [
{
"name": "apply",
"type": "(thisArg: any, argArray?: any) => any"
},
{
"name": "arguments",
"type": "any"
},
{
"name": "bind",
"type": "(thisArg: any, ...argArray: Array<any>) => any"
},
{
"name": "call",
"type": "(thisArg: any, ...argArray: Array<any>) => any"
},
{
"name": "caller",
"type": "any | null"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "length",
"type": "number"
},
{
"name": "name",
"type": "string"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("this.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'this.js', '8', '10'],
'this.js',
).stdout(
`
{
"result": [
{
"name": "bar",
"type": "() => void"
},
{
"name": "baz",
"type": "string"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "hello",
"type": "() => void"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("typeparams.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'typeparams.js', '6', '16'],
'typeparams.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toExponential",
"type": "(fractionDigits?: number) => string"
},
{
"name": "toFixed",
"type": "(fractionDigits?: number) => string"
},
{
"name": "toLocaleString",
"type": "(locales?: (string | Array<string>), options?: Intl$NumberFormatOptions) => string"
},
{
"name": "toPrecision",
"type": "(precision?: number) => string"
},
{
"name": "toString",
"type": "(radix?: number) => string"
},
{
"name": "valueOf",
"type": "() => number"
}
]
}
`,
).exitCodes([0]),
addFile("generics.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'generics.js', '6', '5'],
'generics.js',
).stdout(
`
{
"result": [
{
"name": "cn",
"type": "C<number>"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("optional.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'optional.js', '4', '14'],
'optional.js',
).stdout(
`
{
"result": [
{
"name": "f",
"type": "(x?: string) => void"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "o",
"type": "{x?: string, ...}"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
},
{
"name": "x",
"type": "string | void"
}
]
}
`,
).exitCodes([0]),
addFile("jsx1.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'jsx1.js', '7', '4'],
'jsx1.js',
).stdout(
`
{
"result": [
{
"name": "x",
"type": "number"
}
]
}
`,
).exitCodes([0]),
addFile("jsx2.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'jsx2.js', '7', '9'],
'jsx2.js',
).stdout(
`
{
"result": [
{
"name": "y",
"type": "string"
}
]
}
`,
).exitCodes([0]),
addFile("customfun.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'customfun.js', '6', '1'],
'customfun.js',
).stdout(
`
{
"result": [
{
"name": "idx",
"type": "<IdxObject: any, IdxResult>(obj: IdxObject, pathCallback: (demaybefiedObj: IdxObject) => IdxResult) => ?IdxResult"
},
{
"name": "objectAssign",
"type": "(target: any, ...sources: Array<any>) => any"
},
{
"name": "objectGetPrototypeOf",
"type": "(o: any) => any"
}
]
}
`,
).exitCodes([0]),
addFile("issue-1368.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'issue-1368.js', '20', '10'],
'issue-1368.js',
).stdout(
`
{
"result": [
{
"name": "extended",
"type": "string"
},
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "method",
"type": "() => void"
},
{
"name": "prop",
"type": "number"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("exact.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'exact.js', '7', '5'],
'exact.js',
).stdout(
`
{
"result": [
{
"name": "hasOwnProperty",
"type": "(prop: mixed) => boolean"
},
{
"name": "isPrototypeOf",
"type": "(o: mixed) => boolean"
},
{
"name": "num",
"type": "number"
},
{
"name": "propertyIsEnumerable",
"type": "(prop: mixed) => boolean"
},
{
"name": "str",
"type": "string"
},
{
"name": "toLocaleString",
"type": "() => string"
},
{
"name": "toString",
"type": "() => string"
},
{
"name": "valueOf",
"type": "() => mixed"
}
]
}
`,
).exitCodes([0]),
addFile("exact.js"),
flowCmd(
['autocomplete', '--strip-root', '--json', 'exact.js', '6', '1'],
'exact.js',
).stdout(
`
{
"result": [
{
"name": "obj",
"type": "{|num: number, str: string|}"
}
]
}
`,
).exitCodes([0]),
]),
]): Suite);