Home > Mobile >  React context not updating from default value
React context not updating from default value

Time:12-31

have a login in form, once the login completed i try to set the context to a specific value

import { UserStatus, useUserStatus } from "../context/context";

  const completeLoginAction = async (credentials: any) => {
    var loginSuccess = await authService.login(credentials);
    if (loginSuccess) {
      setUserStatus(1);
      localStorage.setItem("userStatus", JSON.stringify(userStatus));
      console.log("USERSTATIS AFTER LOGIN IS"   userStatus);
      console.log(
        "local storage on login is "   localStorage.getItem("userStatus")
      );
      return true;
    } else {
      return false;
    }
  };

however this is always the default value of 0

even when hardcoding it to 1, its not changing at all

my context.tsx 

import { createContext, useContext } from "react";

export enum UserStatus {
  LoggedOff = 0,
  LoggedIn = 1,
  UserStatus,
}

export type UserStatusContextType = {
  userStatus: UserStatus;
  setUserStatus: (userStatus: UserStatus) => void;
};

export const UserStatusContext = createContext<UserStatusContextType>({
  userStatus: UserStatus.LoggedOff,
  setUserStatus: (userStatus) => console.warn("log on status unknown"),
});

export const useUserStatus = () => useContext(UserStatusContext);

cant workout why it retains the default value and doesnt set the new value

any ideas?

edit: my completed login form

mport React, { useContext, useEffect, useState } from "react";
import Button from "react-bootstrap/Button";
import Form from "react-bootstrap/Form";
import "bootstrap/dist/css/bootstrap.min.css";
import "./LoginPage.css";
import authService from "../../services/authService";
import { Navigate, useNavigate } from "react-router-dom";
import { UserStatus, useUserStatus } from "../context/context";

const LoginPage = () => {
  const [username, setUserName] = useState("");
  const [password, setPassword] = useState("");
  const [errMsg, setErrMsg] = useState("");
  const [sucess, setSuccess] = useState("");

  const { userStatus, setUserStatus } = useUserStatus();

  const navigate = useNavigate();

  const handleUsernameChange = (e: React.ChangeEvent<HTMLInputElement>) => {
    setUserName(e.target.value);
  };

  const handlePasswordChange = (e: React.ChangeEvent<HTMLInputElement>) => {
    setPassword(e.target.value);
  };

  const handleSave = async (e: React.MouseEvent<HTMLButtonElement>) => {
    e.preventDefault();

    const credentials = {
      Username: username,
      Password: password,
    };

    var completed = await completeLoginAction(credentials);

    // if (completed) {
    //   console.log("logged in");
    //   navigate("/");
    // } else {
    //   showErrorMessage();
    // }
  };

  const completeLoginAction = async (credentials: any) => {
    var loginSuccess = await authService.login(credentials);
    if (loginSuccess) {
      setUserStatus(1);
      localStorage.setItem("userStatus", JSON.stringify(userStatus));
      console.log("USERSTATIS AFTER LOGIN IS"   userStatus);
      console.log(
        "local storage on login is "   localStorage.getItem("userStatus")
      );
      return true;
    } else {
      return false;
    }
  };

  const showErrorMessage = () => {
    let elms = document.getElementsByClassName(
      "loginfailmessage"
    ) as HTMLCollectionOf<HTMLElement>;

    for (var i = 0; i < elms.length; i  ) {
      elms[i].style.display = "block";
    }
  };

  return (
    <div className="container">
      <div className="LoginForm">
        <h1 className="Title">Login</h1>
        <Form>
          <Form.Group className="mb-3" controlId="formBasicEmail">
            <Form.Label>Username</Form.Label>
            <Form.Control
              type="text"
              placeholder="Enter username"
              onChange={handleUsernameChange}
              name="username"
              required
            />
          </Form.Group>

          <Form.Group className="mb-3" controlId="formBasicPassword">
            <Form.Label>Password</Form.Label>
            <Form.Control
              type="password"
              placeholder="Password"
              onChange={handlePasswordChange}
              name="password"
              required
            />
          </Form.Group>
          <Button variant="primary" type="submit" onClick={handleSave}>
            Submit
          </Button>
        </Form>
        <h4 className="loginfailmessage" style={{ display: "none" }}>
          Failed to login
        </h4>
      </div>
    </div>
  );
};

export default LoginPage;

CodePudding user response:

MyContext.ts

import { createContext, useContext } from 'react';

export type Status = 'pending' | 'ready';

export type ContextValue = {
    signedIn: boolean,
    status: Status
};

export interface Returns {
    value: ContextValue
    updateValue: (newValue: ContextValue) => void
}

/** defines the default value if none provided */
export const initialValue: ContextValue = {
    signedIn: false,
    status: 'pending'
};

export const MyContext = createContext<ContextValue>({
    value: initialValue,
    updateValue: (newValue) => {
        return console.warn('DefaultContextCallback', newValue);
    }
});

export const useMyContext = () => useContext(MyContext);

App.ts - or however high up it needs to be provided

import React, { useState } from 'react';

import { Component } from 'Component';
import { MyContext, initialValue ) from 'MyContext';

const App = () => {
    const { value , updateValue } = useState(initialValue);

    return (
        <MyContext.Provider value={{ value, updateValue }} >
            <App>
                <Component/>
            </App>
        </MyContext.Provider>
    )
}

Component.tsx

const Component = () => {
    const { value, updateValue } = useMyContext();
}
  • Related