Nested `type()` with an optional property decays to `object`
refi64 opened this issue ยท 6 comments
Report a bug
๐ Search Terms
nested optional object
๐งฉ Context
- ArkType version: 2.0.0-rc0
- TypeScript version (5.1+): 5.5.4
- Other context you think may be relevant (JS flavor, OS, etc.):
๐งโ๐ป Repro
import {ArkErrors, type} from 'arktype'
const T = type({b: type({a: 'number'})}) // Type<{ b: { a: number; }; }, {}>
let t = T({b: {a: 1}})
if (!(t instanceof ArkErrors)) {
console.log(t.b.a) // <-- works
}
const U = type({b: type({'a?': 'number'})}) // Type<{ b: object; }, {}>
let u = U({b: {a: 1}})
if (!(u instanceof ArkErrors)) {
console.log(u.b.a) // <-- ERROR: Property 'a' does not exist on type 'object'.
}
In the first case, the nested type works correctly. In the second case, all I did was change a
to a?
, but that results in the inner type becoming just object
.
Fixed in 2.0.0-rc.2
!
thanks for the fix! but it still seems to happen with a slightly different test case ๐
const U = type({b: type({'a?': 'number'}).or('number')}) // Type<{ b: object; }, {}>
let u = U({b: {a: 1}})
if (!(u instanceof ArkErrors)) {
console.log(u.b.a) // <-- ERROR: Property 'a' does not exist on type 'object'.
}
in particular now I'm calling .or('number')
. It does work if I make it .or
with an object type like .or({'a?': 'number'})}
, though.
@refi64 Also unrelated note you don't have to nest your type calls if you don't need chained expressions- that's the beauty of a parsed syntax!
Just:
const U = type({b: {'a?': 'number'} })
To whatever depth you need!
@refi64 This is actually fixed in 2.0.0-rc.4
!
works now for all my uses, thanks!
Also unrelated note you don't have to nest your type calls if you don't need chained expressions- that's the beauty of a parsed syntax!
Right, this test case was just reduced from the more complex actual usage, where the type was spread out across multiple files.