wouter
wouter copied to clipboard
[proposal] making hooks return object instead of array for readable typeguard
Has there been a discussion about making hooks return object instead of array? The benefits behind that being:
// since typeguard doesn't work with destructuring assignment like this:
const App = () => {
const [match, params] = useRoute<{id: string}>('/path/:id')
if (!match) {
return <div>not present</div>
}
return <div>{params.id}</div> // <- compiler think params may be null
}
// we have to write something like this:
const App = () => {
const route = useRoute<{id: string}>('/path/:id')
if (!route[0]) {
return <div>not present</div>
}
return <div>{route[1].id}</div>
// Not easily understandable what this index accessed variable is, at a glance. Though of course can be avoided
// by assigning another variable with proper name or something, why not: ↓
}
// make it return object like this:
const App = () => {
const route = useRoute<{id: string}>('/path/:id')
if (!route.match) {
return <div>not present</div>
}
return <div>{route.params.id}</div>
}
// by doing the same for useLocation, we don't have to introduce unused variable when using only one of the return values:
const App = () => {
const [_location, setLocation] = useLocation() // <- unused variable
return <button onClick={(e)=>setLocation('somepath')}>
}
const App = () => {
const {setLocation} = useLocation() // <- no unused variable
return <button onClick={(e)=>setLocation('somepath')}>
}
I'm assuming the upside of the current implementation is
- closer signature to well known hooks like
useState()
- in
useRoute
case, some may think receiving array makes it more obvious that the second itemparams
depends on the first itemmatch
, especially for non typescript users
Since this will cause a breaking change and even the subtle benefit isn't obvious for everybody, it might not get enough 👍s. But probably it's still worth discussing once for ppl wondering the same thing later.
(our workaround so far is using a wrapper hook that make it return an object, and also redefining most of return types)
Since this will cause a breaking change
Indeed, this will have a big impact.
@cbbfcd
Thanks for the comment, and yea I guess so! It's a valid decision to not make the change due to ROI, still wanted to make sure if there's any particular intention behind the current design and what other typescript users are feeling about etc.