I'm trying to refactor my context to use a custom hook in TypeScript and I've got an error I don't know how to fix.
This is the error:
This expression is not callable. Not all constituents of type 'boolean | Dispatch<SetStateAction>' are callable. Type 'false' has no call signatures. TS2349
My custom hook is defined like this:
export const useOfflineContext = () => {
const isOffline = React.useContext(OfflineContext);
const setIsOffline = React.useContext(OfflineSetContext);
if (!setIsOffline) {
throw new Error('The OfflineProvider is missing.');
}
return [isOffline, setIsOffline];
};
And I'm calling it like this:
const [setIsOffline] = useOfflineContext();
// Check if we are online or offline.
useEffect(() => {
Network.addListener('networkStatusChange', (networkStatus) => {
// console.log('Network status changed', networkStatus);
if (!networkStatus.connected) {
setIsOffline(true);
This causes the error above.
Here's my full component OfflineContextProvider.tsx:
import React, { useState } from 'react';
const OfflineContext = React.createContext(false);
const OfflineSetContext = React.createContext({} as React.Dispatch<React.SetStateAction<boolean>>);
interface MyProps {
children: JSX.Element,
}
export const OfflineContextProvider: React.VFC<MyProps> = ({ children }: MyProps) => {
const [isOffline, setIsOffline] = useState<boolean>(false);
return (
<OfflineContext.Provider value={isOffline}>
<OfflineSetContext.Provider value={setIsOffline}>
{children}
</OfflineSetContext.Provider>
</OfflineContext.Provider>
);
};
export const useOfflineContext = () => {
const isOffline = React.useContext(OfflineContext);
const setIsOffline = React.useContext(OfflineSetContext);
if (!setIsOffline) {
throw new Error('The OfflineProvider is missing.');
}
return [isOffline, setIsOffline];
};
I don't understand why, when I specifically ask for const [setIsOffline] = useOfflineContext();
, TypeScript thinks that I might want isOffline
instead. (Because the TypeScript warning mentions the boolean value (isOffline).)
So my question is: How can I properly type useState when used in a custom hook to return a context?
Currently using TypeScript 4.3.
CodePudding user response:
You're using the first element of the returned array, which is isOffline
(a boolean), but you're calling it setIsOffline
. However, it is still a boolean.
What you probably want is to get the second element of the array:
const [ , setIsOffline ] = useOfflineContext();