Subscribe on changes!

ReturnType utility breaks Ref type

avatar
Jan 28th 2021

Version

3.0.5

Reproduction link

https://codesandbox.io/s/upbeat-jennings-51bsn?file=/src/index.ts

Steps to reproduce

if I create Ref with ReturnType of some function it will transforms result Ref's to plain type. In this example Ref<boolean> transforms to boolean

type ItemInstance = ReturnType<typeof createItem>;
const arr = ref<ItemInstance[]>([]);

when I push instance to arr I get:

Argument of type '{ isNew: Ref<boolean>; }' is not assignable to parameter of type '{ isNew: boolean; }'.
  Types of property 'isNew' are incompatible.
    Type 'Ref<boolean>' is not assignable to type 'boolean'.ts(2345)

What is expected?

ReturnType returns {isNew: Ref<boolean>}

What is actually happening?

ReturnType returns {isNew: boolean}


I admit that I could not understand correctly how ReturnType works. So maybe I need to go another way to write function which create Item instance

avatar
Jan 28th 2021

You can use a shallowRef to keep underlying refs types untouched: const arr = shallowRef<ItemInstance[]>([]); as a workaround but it could have other impacts (see docs for more information)

avatar
Jul 5th 2022

I would argue that this is a limitation that we can't really change.

the array in the ref has all refs in its items unwrapped, so its type is, correctly, { isNew: Boolean}[].

One can either go the route that posva described, if one wants to preserve the refs, or one can use reactive to also unwrap the item before pushing it, thus getting matching types (this has no influence in the runtime behavior, really:

arr.value.push(reactive(item))