Provide user info in context
This commit is contained in:
		@@ -10,47 +10,33 @@ import {
 | 
			
		||||
  TextField,
 | 
			
		||||
  Typography,
 | 
			
		||||
} from "@mui/material";
 | 
			
		||||
import React, { useRef } from "react";
 | 
			
		||||
import React from "react";
 | 
			
		||||
import { ServerApi } from "../api/ServerApi";
 | 
			
		||||
import { ReplacePasswordResponse, User, UserApi } from "../api/UserApi";
 | 
			
		||||
import { AsyncWidget } from "../widgets/AsyncWidget";
 | 
			
		||||
import { useAlert } from "../widgets/AlertDialogProvider";
 | 
			
		||||
import { useUser } from "../widgets/BaseAuthenticatedPage";
 | 
			
		||||
import { useConfirm } from "../widgets/ConfirmDialogProvider";
 | 
			
		||||
import { PasswordInput } from "../widgets/PasswordInput";
 | 
			
		||||
import { formatDate } from "../widgets/TimeWidget";
 | 
			
		||||
import { useConfirm } from "../widgets/ConfirmDialogProvider";
 | 
			
		||||
import { useAlert } from "../widgets/AlertDialogProvider";
 | 
			
		||||
 | 
			
		||||
export function ProfileRoute(): React.ReactElement {
 | 
			
		||||
  const [user, setUser] = React.useState<null | User>(null);
 | 
			
		||||
 | 
			
		||||
  const load = async () => {
 | 
			
		||||
    const u = await UserApi.GetUserInfo();
 | 
			
		||||
    setUser(u);
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  const counter = useRef(0);
 | 
			
		||||
  const user = useUser();
 | 
			
		||||
 | 
			
		||||
  return (
 | 
			
		||||
    <AsyncWidget
 | 
			
		||||
      loadKey={counter.current}
 | 
			
		||||
      load={load}
 | 
			
		||||
      errMsg="Echec du chargement des informations du compte utilisateur !"
 | 
			
		||||
      build={() => (
 | 
			
		||||
        <div style={{ maxWidth: "500px", margin: "auto" }}>
 | 
			
		||||
          <Typography variant="h3">Profil</Typography>
 | 
			
		||||
    <div style={{ maxWidth: "500px", margin: "auto" }}>
 | 
			
		||||
      <Typography variant="h3">Profil</Typography>
 | 
			
		||||
 | 
			
		||||
          <ProfileSettingsCard
 | 
			
		||||
            user={user!}
 | 
			
		||||
            onUpdate={() => (counter.current += 1)}
 | 
			
		||||
          />
 | 
			
		||||
          {user?.has_password && <ChangePasswordCard />}
 | 
			
		||||
          <DeleteAccountButton />
 | 
			
		||||
        </div>
 | 
			
		||||
      )}
 | 
			
		||||
    />
 | 
			
		||||
      <ProfileSettingsCard
 | 
			
		||||
        user={user.user}
 | 
			
		||||
        onUpdate={() => user.reloadUserInfo()}
 | 
			
		||||
      />
 | 
			
		||||
      {user.user.has_password && <ChangePasswordCard />}
 | 
			
		||||
      <DeleteAccountButton />
 | 
			
		||||
    </div>
 | 
			
		||||
  );
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function ProfileSettingsCard(p: { user: User; onUpdate: () => {} }) {
 | 
			
		||||
function ProfileSettingsCard(p: { user: User; onUpdate: () => void }) {
 | 
			
		||||
  const [newName, setNewName] = React.useState(p.user.name);
 | 
			
		||||
 | 
			
		||||
  const [error, setError] = React.useState<string | null>(null);
 | 
			
		||||
 
 | 
			
		||||
@@ -15,6 +15,13 @@ import { User, UserApi } from "../api/UserApi";
 | 
			
		||||
import { AsyncWidget } from "./AsyncWidget";
 | 
			
		||||
import { RouterLink } from "./RouterLink";
 | 
			
		||||
 | 
			
		||||
interface UserContext {
 | 
			
		||||
  user: User;
 | 
			
		||||
  reloadUserInfo: () => void;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const UserContextK = React.createContext<UserContext | null>(null);
 | 
			
		||||
 | 
			
		||||
export function BaseAuthenticatedPage(): React.ReactElement {
 | 
			
		||||
  const [user, setUser] = React.useState<null | User>(null);
 | 
			
		||||
 | 
			
		||||
@@ -48,69 +55,80 @@ export function BaseAuthenticatedPage(): React.ReactElement {
 | 
			
		||||
      load={load}
 | 
			
		||||
      errMsg="Echec du chargement des informations utilisateur !"
 | 
			
		||||
      build={() => (
 | 
			
		||||
        <div
 | 
			
		||||
          style={{
 | 
			
		||||
            minHeight: "100vh",
 | 
			
		||||
            display: "flex",
 | 
			
		||||
            flexDirection: "column",
 | 
			
		||||
        <UserContextK.Provider
 | 
			
		||||
          value={{
 | 
			
		||||
            user: user!,
 | 
			
		||||
            reloadUserInfo: load,
 | 
			
		||||
          }}
 | 
			
		||||
        >
 | 
			
		||||
          <AppBar position="sticky">
 | 
			
		||||
            <Toolbar>
 | 
			
		||||
              <Icon
 | 
			
		||||
                path={mdiFamilyTree}
 | 
			
		||||
                size={1}
 | 
			
		||||
                style={{ marginRight: "1rem" }}
 | 
			
		||||
              />
 | 
			
		||||
          <div
 | 
			
		||||
            style={{
 | 
			
		||||
              minHeight: "100vh",
 | 
			
		||||
              display: "flex",
 | 
			
		||||
              flexDirection: "column",
 | 
			
		||||
            }}
 | 
			
		||||
          >
 | 
			
		||||
            <AppBar position="sticky">
 | 
			
		||||
              <Toolbar>
 | 
			
		||||
                <Icon
 | 
			
		||||
                  path={mdiFamilyTree}
 | 
			
		||||
                  size={1}
 | 
			
		||||
                  style={{ marginRight: "1rem" }}
 | 
			
		||||
                />
 | 
			
		||||
 | 
			
		||||
              <Typography variant="h6" component="div" sx={{ flexGrow: 1 }}>
 | 
			
		||||
                <RouterLink to="/">GeneIT</RouterLink>
 | 
			
		||||
              </Typography>
 | 
			
		||||
                <Typography variant="h6" component="div" sx={{ flexGrow: 1 }}>
 | 
			
		||||
                  <RouterLink to="/">GeneIT</RouterLink>
 | 
			
		||||
                </Typography>
 | 
			
		||||
 | 
			
		||||
              <div>
 | 
			
		||||
                <Button size="large" color="inherit">
 | 
			
		||||
                  {user!.name}
 | 
			
		||||
                </Button>
 | 
			
		||||
                <div>
 | 
			
		||||
                  <Button size="large" color="inherit">
 | 
			
		||||
                    {user!.name}
 | 
			
		||||
                  </Button>
 | 
			
		||||
 | 
			
		||||
                <Button
 | 
			
		||||
                  size="large"
 | 
			
		||||
                  aria-label="account of current user"
 | 
			
		||||
                  aria-controls="menu-appbar"
 | 
			
		||||
                  aria-haspopup="true"
 | 
			
		||||
                  onClick={handleMenu}
 | 
			
		||||
                  color="inherit"
 | 
			
		||||
                >
 | 
			
		||||
                  <SettingsIcon />
 | 
			
		||||
                </Button>
 | 
			
		||||
                <Menu
 | 
			
		||||
                  id="menu-appbar"
 | 
			
		||||
                  anchorEl={anchorEl}
 | 
			
		||||
                  anchorOrigin={{
 | 
			
		||||
                    vertical: "top",
 | 
			
		||||
                    horizontal: "right",
 | 
			
		||||
                  }}
 | 
			
		||||
                  keepMounted
 | 
			
		||||
                  transformOrigin={{
 | 
			
		||||
                    vertical: "top",
 | 
			
		||||
                    horizontal: "right",
 | 
			
		||||
                  }}
 | 
			
		||||
                  open={Boolean(anchorEl)}
 | 
			
		||||
                  onClose={handleCloseMenu}
 | 
			
		||||
                >
 | 
			
		||||
                  <Link
 | 
			
		||||
                    to="/profile"
 | 
			
		||||
                    style={{ color: "inherit", textDecoration: "none" }}
 | 
			
		||||
                  <Button
 | 
			
		||||
                    size="large"
 | 
			
		||||
                    aria-label="account of current user"
 | 
			
		||||
                    aria-controls="menu-appbar"
 | 
			
		||||
                    aria-haspopup="true"
 | 
			
		||||
                    onClick={handleMenu}
 | 
			
		||||
                    color="inherit"
 | 
			
		||||
                  >
 | 
			
		||||
                    <MenuItem onClick={handleCloseMenu}>Profil</MenuItem>
 | 
			
		||||
                  </Link>
 | 
			
		||||
                  <MenuItem onClick={signOut}>Déconnexion</MenuItem>
 | 
			
		||||
                </Menu>
 | 
			
		||||
              </div>
 | 
			
		||||
            </Toolbar>
 | 
			
		||||
          </AppBar>
 | 
			
		||||
          <Outlet />
 | 
			
		||||
        </div>
 | 
			
		||||
                    <SettingsIcon />
 | 
			
		||||
                  </Button>
 | 
			
		||||
                  <Menu
 | 
			
		||||
                    id="menu-appbar"
 | 
			
		||||
                    anchorEl={anchorEl}
 | 
			
		||||
                    anchorOrigin={{
 | 
			
		||||
                      vertical: "top",
 | 
			
		||||
                      horizontal: "right",
 | 
			
		||||
                    }}
 | 
			
		||||
                    keepMounted
 | 
			
		||||
                    transformOrigin={{
 | 
			
		||||
                      vertical: "top",
 | 
			
		||||
                      horizontal: "right",
 | 
			
		||||
                    }}
 | 
			
		||||
                    open={Boolean(anchorEl)}
 | 
			
		||||
                    onClose={handleCloseMenu}
 | 
			
		||||
                  >
 | 
			
		||||
                    <Link
 | 
			
		||||
                      to="/profile"
 | 
			
		||||
                      style={{ color: "inherit", textDecoration: "none" }}
 | 
			
		||||
                    >
 | 
			
		||||
                      <MenuItem onClick={handleCloseMenu}>Profil</MenuItem>
 | 
			
		||||
                    </Link>
 | 
			
		||||
                    <MenuItem onClick={signOut}>Déconnexion</MenuItem>
 | 
			
		||||
                  </Menu>
 | 
			
		||||
                </div>
 | 
			
		||||
              </Toolbar>
 | 
			
		||||
            </AppBar>
 | 
			
		||||
            <Outlet />
 | 
			
		||||
          </div>
 | 
			
		||||
        </UserContextK.Provider>
 | 
			
		||||
      )}
 | 
			
		||||
    />
 | 
			
		||||
  );
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export function useUser(): UserContext {
 | 
			
		||||
  return React.useContext(UserContextK)!;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user