Reputation: 799
My code is as follows:
export function testGraph({ id = 0, name = "test", nodes = [] }): Graph {
if (nodes.length === 0) {
const dummyNode = testNode({});
return new Graph(id, name, [dummyNode]);
}
return new Graph(id, name, nodes);
}
export function testDatabase({ id = 0, name = "test", graphs = [] }): Database {
if (graphs.length === 0) {
const dummyGraph = testGraph({ nodes: new Array(new Node(0)) });
return new Database(id, name, [dummyGraph]);
}
return new Database(id, name, graphs);
}
But this gives me the following error:
Type 'Node[]' is not assignable to type 'never[]'.
Type 'Node' is not assignable to type 'never'.
40 const dummyGraph = testGraph({ nodes: new Array(new Node(0)) });
~~~~~
I can't seem to understand why this is automatically inferring 'never' type. I tried explicitly declaring the type but to no luck.
Upvotes: 1
Views: 614
Reputation: 187004
nodes = []
. An array of what?
[]
is never enough to for typescript to infer an array type, and is inferred as never[]
in this particular case. So, typically, you just provide a type for the whole destructured object, and include the proper array type:
export function testGraph({
id = 0,
name = "test",
nodes = []
}: {
id?: number,
name?: string,
nodes?: Node[]
}): Graph {
//...
}
Or infer from the caller by using generics.
export function testGraph<T>({
id = 0,
name = "test",
nodes = []
}: {
id?: number,
name?: string,
nodes?: T[]
}): Graph<T> {
//...
}
Note that you'll probably want to make Graph
generic as well, so that the node type you pass to testGraph
can be reflected in the Graph
's nodes as well.
That might look something like:
class Graph<T> {
constructor(id: number, name: string, nodes: T[]) {
//...
}
}
Upvotes: 1
Reputation: 55856
This discussion on Github puts some light on the issue:
This is caused by the combination of
strict
andnoImplicitAny: false
. In general we expect that ifstrict
is on,noImplicitAny
is also on; this particular set of settings will expose some odd behavior. If you had both on, you'd see an error about the[]
being implicitlyany[]
; if both were off; we'd use control flow analysis and treat the array as anumber[]
after the push(1);.The particular combination (
"strict": true, "noImplicitAny": false,
) of settings means that we don't allow ourselves to use control flow analysis or allow the array to be implicitlyany[]
, sonever[]
is the only remaining allowable option.I'd recommend turning off
strict
if you're not going to havenoImplicitAny
on.
So, this may be a possible way out
export function testGraph({ id = 0, name = "test", nodes = [] as Array<Node> }): Graph {
...
Upvotes: 1