TypeScript: T implicitly has type 'any' because it does not have a type annotation and is referenced directly or indirectly in its own initializer
TypeScript Version: 3.7.3
Code
type Schema = {
[key: string]: Number | String | Boolean | (() => Model<any>)
}
type Model<T extends Schema> = {
}
function model<T extends Schema>(type: Schema): Model<T> {
return undefined as any
}
const User = model({
id: Number,
name: String,
photo: () => Photo
})
const Photo = model({
id: Number,
filename: String,
user: () => User
})
Expected behavior:
No errors. I need this technic to implement automatically inferred circular types. I already have a class-based implementation (you can see example here) and I basically want same with objects of course without manually defining its type. If it’s not a bug, any advances on how to implement it keeping type inferred are highly appreciated.
Actual behavior:
Gives following error:
'User' implicitly has type 'any' because it does not have a type annotation and is referenced directly or indirectly in its own initializer.(7022)
About this issue
- Original URL
- State: closed
- Created 5 years ago
- Reactions: 37
- Comments: 25 (4 by maintainers)
Having similar issue with very simple example
Would really want to know if this is temporary limitation or rather impossible to solve limitation?
(FYI - ignore that input in someFunc is never called. It can be called in async context. This example is simplified to show the problem)
Tested with TS 3.8.3
Playground link: https://www.typescriptlang.org/play/#code/PTAEFpK6FgCgSgIIBkWgPIGlQAsCmATvgDSgC2AnhgEYBW+AxgC4CMeAhgM6gcA2fUM0oAHfDwAm+ZkxkT4jAPYA7LswrV6s9gF5QAb3ihjvDhwBcoAKwAGEkZM0nlgBQBKUDoB8BhyZPEzACuhMoatAwsrAB0ZhwA3H6gAL7wyYlw8IjQOeBZYFQRsgBMnDxK5CIAlnwczFUqoESEioSuAOpVzLigaoRVLBSKUpgAcm75oAAqoFWVfANdfJRlQqL4oADkHMqUm6A0TBxBXBtdoBKK4qDKiuq4HABuGxxrYrzKt8x1DcqT-jsJLMeMQAGZEfDKRj4IESKrEFjLUCtWbKOEI5hIqphLo8RQAdxxyi6VX4VQAXkQFCo1L1FOR8AAxIJQzygFzYkRBZiuDzeG5BciHQhuSx9bEAc08PkMcH8gRCYQARDJaUqMul4NTVOpCloWKU9LKAWZLLZ7HLHM46QzmVCXO5pb5Lf5jArQuF9cxirEzBl-MkJnBNXAgA
EDIT 1: In our case someFunc is async. Sync can’t work, as object is not defined property by property, but all at once. That explains why this is an error. Problem is that it depends how people use it. In sync context it is error for obvious reasons, in async (when at least one tick is passed) it would work fine.
EDIT 2: Whoever is stuck with this, for us alternative approach worked OK: This behaves pretty much same as object definition, but class is created property by property.
Simplified example:
Note:
| undefined
is removed on type ofa
a = b;
is removed or inlined toa = await getAString(a);
getAString
is not asyncPlayground Link
I originally ran into this problem trying to use aws-sdk paginated service methods, which often have a
NextToken
property taking the place ofa
in my contrived example. The above was just as simplified as I could make it. The actual workaround I used was to declare my variable outside the loop asany
.I am getting this in an even simpler case:
You can try it out:
However,
a
should clearly be of typenumber
, based on the way Javascript destructuring works.Here’s another example with firebase auth and TS 4.2.3.
We are using the same pattern with the gmail api, the only difference there is how the page token is specified. Instead of being it’s own argument the gmail api received the
pageToken
in an options param, as in:Please don’t interpret any of this as impatience or offense; I’m not sure why this happens either and also find it odd!
What I’m trying to say is that circularity errors on circularities are not per se defects, and I’m not going to reallocate finite team resources away from fixing defects or implementing features toward addressing non-defects.
The investigation itself here is the resource spend that I’m trying to avoid. Figuring out why a thing happens is usually 80% of fixing it.
Another example:
Playground
Small non-circular example. Error shows up on the line that says “error here”
Removing the line 2 down (the
property = records.property
, then there is no more error.also if I break out the await onto 2 lines, the error goes away:
I have the same issue with
await
keyword:Without
await
keyword I getWith
await
keyword I getThis also happens to me when I try to use the
aws-sdk
It infers
Parameters: AWS.ParameterList
, but gives me the same error onNextToken
EDIT: I started out with the below example and that works:
Apparently, the circularity is in
input
? But it is detected only onNextToken
(and not onParameters
)