0

I have the following code:

let foo: { a: { b: { c: number }}} | undefined;

foo?.a.b.c

As far I understand, only the foo variable should be typed as | undefined. But for some reason each path inside it is also marked as | undefined:

enter image description here

enter image description here

This doesn't make sense to me based on the compiled code that only checks the foo variable:

let foo;
foo === null || foo === void 0 ? void 0 : foo.a.b.c;

My expectation is that if foo is not undefined, the rest of the path is guaranteed to exists. Am I wrong?

1
  • I believe that the type you see in the popup is inferred from the entire expression up to that part of the expression that you are hovering. Reading it in isolation is perhaps misleading. Commented Aug 9, 2021 at 14:51

1 Answer 1

1

In case foo is undefined, foo.a.b.c won't have a value, hence it will be undefined. If foo is an object it will be a number. Consider the following example

let foo: { a: { b: { c: number }}} | undefined;

// if foo is undefined the whole expression may be undefined
const result1 = foo?.a.b.c

const fn = (param: typeof foo): number => {
  // if you ensude that param isn't undefined
  if( !param ) {
    throw new Error()
  }

  // then a.b.c is guraranteed to be a number
  return param.a.b.c;
}

playground

Sign up to request clarification or add additional context in comments.

2 Comments

I see what you mean, but this is confusing. It would make sense if typescript would force me to do: foo?.a?.b?.c - because based on the type in the images, every property could be undefined.
I don't agree. If you were to write checks if properties exists you'd need to just check if a exists on foo and the rest would be guaranteed to be there.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.