-
Notifications
You must be signed in to change notification settings - Fork 12.8k
Checking existence of entry in Record<string, Promise<string>> always yields "This condition will always return true since this 'Promise<string>' is always defined" #56203
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. Weβll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
This is working as intended. You need to enable the |
Yes enabling If that is the case, why is it not consistent so an error is also produced if the cache was typed as const cache: Record<string, string> = {}; This produces no error even though it should be the same if it were consistent: |
Because strings can be falsy ( |
No, that is not it const cache: Record<string, object> = {};
function getPromise(key: string) {
if (cache[key]) {
return 'Found';
}
return 'Not found';
} yields no error as well. There seems to be a special case for promises which is not consistent with "normal" objects. |
That should be an error, yeah. Either way, the root cause here is still that |
@MartinJohns, why is the behaviour different when having a @fatcerberus, yes. Enabling However, it still seems like a bug to me that the behaviour is different just because the record contains a special type of object ( |
Itβs not just because itβs a βspecial type of objectβ, but because itβs an object type at all being checked for truthiness when objects are known by the compiler to always be truthy. (The fact that it doesnβt show the error for
Yes, but index signatures such as the one on The same thing applies to accessing arbitrary indices of an array, for what itβs worth. |
@fatcerberus, ok, so what you are saying is that the bug is that the error only shows for Promise and not any other object type (including user defined types)? I am not entirely sure I agree, but I guess that is a design decision for the TS team which way to go. But we agree that it should behave the same regardless of whether the values in the record are promises or any other object type, right? In any case, the hint about Example with user defined type (instead of |
That's a long standing design limitation involving Can't say anything other than "this is working as expected" and that enabling |
Duplicate of #55852, which is marked "Working as Intended". Not 100 % exact, but essentially the same issue: assuming record access could yield in |
@MartinJohns Please see this example. This example does not allow assigning falsy primitives yet still is inconsistent. const key: string = 'someKey';
const a: Record<string, Promise<string>> = {};
const b: Record<string, {a: string}> = {};
// errors here with message about using await
if (a[key]) console.log('found');
// but not here
if (b[key]) console.log('found') Would you also say that is working as intended? If not, would it be better to open a new issue describing the inconsistent behaviour in the code above? |
I disagree that this is a duplicate, since the issue I am (trying to) describe is the inconsistent behaviour when accessing these two records without const a: Record<string, Promise<string>> = {};
const b: Record<string, {a: string}> = {}; |
Oh, the error you're seeing is the "did you forget to use const foo = getFooAsync(); // returns a promise
if (foo) { // oops, always truthy but you probably just forgot to await the promise
// do stuff
} |
In that case it's also intentional, see #25330 (this also matches your changed between versions). This behaviour is irregardless of using a With
No sweat. |
Alright, I guess I hit an interesting edge case where I have not (yet) enabled The hint about using await makes sense in most other cases and I agree that it would be probably be hard to improve the message for this special case. Thanks for clearing that up for me π |
Uh oh!
There was an error while loading. Please reload this page.
π Search Terms
This condition will always return true since this 'Promise' is always defined
Record promises
π Version & Regression Information
β― Playground Link
https://www.typescriptlang.org/play?#code/MYewdgzgLgBADgJxAWwJYQKYGECGwAWGAXDAEoagIAmAPNAqmAOYA0MACkmpnVA8wD4BMALwwA3gF8A3AChZAMwCuYYFFTgYTDFE4p0GABQBrDAE8S9RkwCUE2TEcxUCmIcT7MuAhgDapswBdO3EHJ3CEHSUEMBgAcgAxEBUqOLlwyTDHSKho2LiAORBYBWSwVLlMoA
π» Code
π Actual behavior
It should be clear that
promiseCache[key]
is not always defined, and that this has nothing to do with it containing promises or a missing await. It is just a record of objects which happen to be promisesπ Expected behavior
There should not be an error, since
Is a valid check in this case
Additional information about the issue
No response
The text was updated successfully, but these errors were encountered: