Hello so i'm new to typescript react and currently trying to make applications using typescript and tutorial from youtube.
const RegisterCustomer: React.FC = () => {
const [text, setText] = useState<string>('');
const [email, setEmail] = useState<string>('');
const [username, setUsername] = useState<string>('');
const [password, setPassword] = useState<string>('');
const [isSubmitting, setIsSubmitting] = useState(false);
const { register } = useAuth();
return (
<IonPage>
<Register />
<IonContent className="body">
<IonGrid className="gridinput1">
</IonGrid>
<IonGrid className="gridinput2">
<IonRow>
<IonInput type="email" className="inputEmail" value={email} placeholder="Email" onIonChange={e => setEmail(e.detail.value!)}></IonInput>
</IonRow>
</IonGrid>
<IonGrid className="gridinput3">
<IonRow>
<IonInput type="password" className="inputEmail" value={password} placeholder="Password" onIonChange={e => setPassword(e.detail.value!)}></IonInput>
</IonRow>
</IonGrid>
<IonGrid className="gridinput1">
<IonRow>
<IonButton onClick={async e =>{
e.preventDefault()
const res = await register(email, password);
if(res) {
console.log(res);
}
else {
//handle null response
}
console.log(email, password)
}} className="buttonLogin" expand="block" size="default" color="new">
Register Now
</IonButton>
</IonRow>
</IonGrid>
<p className="loginSeller"><a href="https://www.w3schools.com/">Are you a seller? Login as Seller</a></p>
</IonContent>
</IonPage>
);
};
export default RegisterCustomer;
and this is the authContext
type ButtonProps = {
children: ReactNode;
}
export const useAuth = () =>useContext(AuthContext);
type AuthContextType = {
currentUser: null;
register: (
email: string,
password: string
) => Promise<UserCredential | undefined>;
};
const AuthContext = createContext<Partial<AuthContextType>>({}); // Partial
export default function AuthContextProvider( { children} : ButtonProps){
const [currentUser, setCurrentUser] = useState(null);
function register(email: string, password:string) {
return createUserWithEmailAndPassword(auth, email, password)
}
const value = {
currentUser,
register,
}
return <AuthContext.Provider value={value}>
{children}
</AuthContext.Provider>
}
im trying to get the data from register to firebase but i encounter error " Cannot invoke an object which is possibly 'undefined'. " in register.then in RegisterCustomer page. How do i solve this problem
CodePudding user response:
Since you expect the register
property to always exist, adjust your types so that it remains as a required property:
const AuthContext = createContext<Partial<Omit<AuthContextType, "register">> & Pick<AuthContextType, "register">>({});
Here, the type is broken into two pieces. The Partial<Omit<AuthContextType, "register">>
creates a type that removes the register
property and marks everything else as optional. The Pick<AuthContextType, "register">
creates a type that only has the register
property. We combine those together using an intersection (&
) to get the final type which makes everything except register
optional.
This will produce an additional error since you are passing {}
as the default value, but the type indicates that a register
property must be present on that context. Since it is merely the default and you overwrite it when using the provider, I would recommend passing a no-op function to it as the default register
value. Eg:
const AuthContext = createContext<Partial<Omit<AuthContextType, "register">> & Pick<AuthContextType, "register">>({register: async () => undefined});