Skip to content
Snippets Groups Projects
Groups.js 10.2 KiB
Newer Older
import React, { useEffect, useState } from "react";
Larbi Gharib's avatar
Larbi Gharib committed
import { Link, useHistory } from "react-router-dom";
// @mui/material components
import { makeStyles } from "@mui/styles";
// core components
import GridItem from "components/Grid/GridItem.js";
import GridContainer from "components/Grid/GridContainer.js";
import Button from "components/CustomButtons/Button.js";
import Card from "components/Card/Card.js";
import CardBody from "components/Card/CardBody.js";
import CardFooter from "components/Card/CardFooter.js";
William Enright's avatar
William Enright committed
import CustomInput from "components/CustomInput/CustomInput.js";

import IconButton from "@mui/material/IconButton";
import DeleteOutlineIcon from "@mui/icons-material/DeleteOutline";
import Search from "@mui/icons-material/Search";
import MailOutlineIcon from "@mui/icons-material/MailOutline";
import PersonIcon from "@mui/icons-material/Person";
import InfoIcon from "@mui/icons-material/Info";
William Enright's avatar
William Enright committed

import axios from "axios";
import configApiCall from "api.js";
Larbi Gharib's avatar
Larbi Gharib committed
import auth from "auth.js";
import {
  api_path_get_list_group,
  api_path_delete_group,
  api_path_get_group_members,
Larbi Gharib's avatar
Larbi Gharib committed
} from "globalUrls";

import AddCircleOutlineIcon from "@mui/icons-material/AddCircleOutline";
William Enright's avatar
William Enright committed

import Dialog from "@mui/material/Dialog";
import DialogActions from "@mui/material/DialogActions";
import DialogContent from "@mui/material/DialogContent";
import DialogContentText from "@mui/material/DialogContentText";
import DialogTitle from "@mui/material/DialogTitle";
William Enright's avatar
William Enright committed

import LinearProgress from "@mui/material/LinearProgress";
Larbi Gharib's avatar
Larbi Gharib committed
import i18next from "i18next";

import CreateGroupDialog from "./CreateGroupDialog";
const styles = {
Larbi Gharib's avatar
Larbi Gharib committed
  cardCategoryWhite: {
    color: "rgba(255,255,255,.62)",
    margin: "0",
    fontSize: "14px",
    marginTop: "0",
    marginBottom: "0",
  },
  cardTitleWhite: {
    color: "#FFFFFF",
    marginTop: "0px",
    minHeight: "auto",
    fontWeight: "300",
    fontFamily: "'Roboto', 'Helvetica', 'Arial', sans-serif",
    marginBottom: "3px",
    textDecoration: "none",
  },
  deleteIcon: {
    float: "right",
  },
  search: {
    width: "90%",
  },
  loading: {
    width: "100%",
  },
  groupsNotFound: {
    marginLeft: "10px",
    display: "flex",
    alignItems: "center",
  },
Larbi Gharib's avatar
Larbi Gharib committed
  whiteButtonText: {
    color: "white",
Larbi Gharib's avatar
Larbi Gharib committed
  },
  inputBottomMargin: {
};

const useStyles = makeStyles(styles);

export default function Groups() {
Larbi Gharib's avatar
Larbi Gharib committed
  const classes = useStyles();
  const history = useHistory();
  const [groups, setGroups] = useState([]);
  const [loading, setLoading] = useState(false);
  const [zeroGroup, setZeroGroup] = useState(false);
  const [progress, setProgress] = useState(0);
  const [searchValue, setSearchValue] = useState(null);
  const [openCreate, setOpenCreate] = useState(false);
  const [removedGroup, setRemovedGroup] = useState({
Larbi Gharib's avatar
Larbi Gharib committed
  });
  const [openRemoveDialog, setOpenRemoveDialog] = useState(false);
Larbi Gharib's avatar
Larbi Gharib committed
  const handleRemoveGroup = (group) => {
    setRemovedGroup(group);
Larbi Gharib's avatar
Larbi Gharib committed
    setOpenRemoveDialog(true);
  };

  const removeGroup = () => {
    axios(
      configApiCall(
Larbi Gharib's avatar
Larbi Gharib committed
        api_path_delete_group + removedGroup.id,
Larbi Gharib's avatar
Larbi Gharib committed
        "DELETE",
        null,
        null
      )
    )
Larbi Gharib's avatar
Larbi Gharib committed
        console.log("Successfully deleted " + removedGroup.name);
Larbi Gharib's avatar
Larbi Gharib committed
        setOpenRemoveDialog(false);
      })
      .catch((error) => {
Larbi Gharib's avatar
Larbi Gharib committed
        console.log("Could not delete " + removedGroup.name + " " + error);
Larbi Gharib's avatar
Larbi Gharib committed
        setOpenRemoveDialog(false);
      });

    history.push("/groups");
Larbi Gharib's avatar
Larbi Gharib committed
  };

  useEffect(() => {
    setLoading(true);
    const timer = setInterval(() => {
      setProgress((oldProgress) => {
        if (oldProgress === 100) {
          return 0;
        }
        const diff = Math.random() * 10;
        return Math.min(oldProgress + diff, 100);
      });
    }, 500);

    axios(configApiCall(api_path_get_list_group, "GET", null, null))
Larbi Gharib's avatar
Larbi Gharib committed
      .then((response) => {
        let allGroups = response.data;
        allGroups.forEach((group) => {
          axios(
            configApiCall(
              api_path_get_group_members + group.id,
              "GET",
              null,
              null
            )
          )
            .then((response) => {
              group["groupMembersLength"] = response.data.length;
            })
            .catch((error) => {
              if (error.response.status === 401) {
                auth.authenticated = false;
                history.push("/");
              }
              if (error.response.status === 404) {
                group["groupMembersLength"] = 0;
              }
            });
        });
Larbi Gharib's avatar
Larbi Gharib committed
        setGroups(allGroups);
Larbi Gharib's avatar
Larbi Gharib committed
        setLoading(false);
      })
      .catch((error) => {
        if (error.response.status === 401) {
          auth.authenticated = false;
          history.push("/signin");
        if (error.response.status === 404) {
Larbi Gharib's avatar
Larbi Gharib committed
          setZeroGroup(true);
        }
Larbi Gharib's avatar
Larbi Gharib committed
      });
    return () => {
      clearInterval(timer);
    };
Larbi Gharib's avatar
Larbi Gharib committed
  }, [openCreate, openRemoveDialog, history]);
Larbi Gharib's avatar
Larbi Gharib committed

  if (!auth.hasAdminScope()) {
    return (
      <div>
        <h4>
          {i18next.t(
            "you_are_not_allowed_to_access_this_section",
            "You are not allowed to access this section. Please contact your administrator to get administrator privileges."
          )}
Larbi Gharib's avatar
Larbi Gharib committed
        </h4>
      </div>
    );
Larbi Gharib's avatar
Larbi Gharib committed
    return (
      <div>
        <CreateGroupDialog
          openCreate={openCreate}
          setOpenCreate={setOpenCreate}
          classes={classes}
        />
Larbi Gharib's avatar
Larbi Gharib committed
        <Dialog
          open={openRemoveDialog}
          onClose={() => setOpenRemoveDialog(false)}
          aria-labelledby="alert-dialog-title"
          aria-describedby="alert-dialog-description"
        >
          <DialogTitle id="alert-dialog-title">
            {i18next.t("remove_group", "Remove group")}
          </DialogTitle>
Larbi Gharib's avatar
Larbi Gharib committed
          <DialogContent>
            <DialogContentText id="alert-dialog-description">
              {i18next.t(
                "are_you_sure_you_want_to_delete",
                "Are you sure you want to delete"
              )}{" "}
              <strong>{removedGroup.name}</strong> ?
Larbi Gharib's avatar
Larbi Gharib committed
            </DialogContentText>
          </DialogContent>
          <DialogActions>
            <Button onClick={() => setOpenRemoveDialog(false)} color="primary">
Larbi Gharib's avatar
Larbi Gharib committed
              {i18next.t("cancel", "Cancel")}
Larbi Gharib's avatar
Larbi Gharib committed
            </Button>
            <Button onClick={removeGroup} color="info" autoFocus>
Larbi Gharib's avatar
Larbi Gharib committed
              {i18next.t("remove", "Remove")}
Larbi Gharib's avatar
Larbi Gharib committed
            </Button>
          </DialogActions>
        </Dialog>
        <GridContainer>
          <GridItem xs={12} sm={12} md={12}>
            {
              <Button
                variant="contained"
                color="primary"
                href="#contained-buttons"
                onClick={() => setOpenCreate(true)}
                <AddCircleOutlineIcon />{" "}
                {i18next.t("create_group", "Create group")}
Larbi Gharib's avatar
Larbi Gharib committed
              </Button>
            }
            <div className={classes.searchWrapper}>
              {!zeroGroup && (
                <CustomInput
                  formControlProps={{
                    className: classes.margin + " " + classes.search,
                  }}
                  inputProps={{
                    placeholder: i18next.t(
                      "search_groups_placeholder",
                      "Search groups…"
                    ),
Larbi Gharib's avatar
Larbi Gharib committed
                    inputProps: {
Larbi Gharib's avatar
Larbi Gharib committed
                      "aria-label": i18next.t("search_groups", "Search groups"),
Larbi Gharib's avatar
Larbi Gharib committed
                    },
                    onKeyUp: (e) => setSearchValue(e.target.value),
                  }}
William Enright's avatar
William Enright committed
                />
Larbi Gharib's avatar
Larbi Gharib committed
              )}
              {!zeroGroup && <Search />}
              <div className={classes.loading}>
                {!zeroGroup && loading && (
Larbi Gharib's avatar
Larbi Gharib committed
                  <LinearProgress variant="determinate" value={progress} />
                )}
              </div>
William Enright's avatar
William Enright committed
            </div>
Larbi Gharib's avatar
Larbi Gharib committed
          </GridItem>
          {zeroGroup ? (
            <div className={classes.groupsNotFound}>
              <InfoIcon />{" "}
              <p style={{ marginLeft: "10px" }}>
                {i18next.t("no_groups_found", "No groups Found")}
              </p>
William Enright's avatar
William Enright committed
            </div>
Larbi Gharib's avatar
Larbi Gharib committed
          ) : (
Larbi Gharib's avatar
Larbi Gharib committed
            groups
              .filter((data) => {
                if (searchValue === null) {
                  return data;
                } else {
                  return data.name
                    .toLowerCase()
                    .includes(searchValue.toLowerCase());
                }
              })
              .map((group) => (
                <GridItem xs={12} sm={6} md={3} lg={2} xl={2} key={group.name}>
Larbi Gharib's avatar
Larbi Gharib committed
                  <Card profile>
Larbi Gharib's avatar
Larbi Gharib committed
                    <Link to={`/group/${group.id}`}>
Larbi Gharib's avatar
Larbi Gharib committed
                        <h3 className={classes.cardTitle}>{group.name}</h3>
                        <ul>
                          <li>
                            <PersonIcon
                              fontSize="small"
                              style={{ marginRight: "10px" }}
                            />
                            <strong style={{ marginRight: "5px" }}>
Larbi Gharib's avatar
Larbi Gharib committed
                              {group.groupMembersLength}
Larbi Gharib's avatar
Larbi Gharib committed
                            </strong>
Larbi Gharib's avatar
Larbi Gharib committed
                            {i18next.t("users", "users")}
Larbi Gharib's avatar
Larbi Gharib committed
                          </li>
                          <li>
                            <MailOutlineIcon
                              fontSize="small"
                              style={{ marginRight: "10px" }}
                            />
                            <strong style={{ marginRight: "5px" }}>
Larbi Gharib's avatar
Larbi Gharib committed
                              {i18next.t("blueprint", "Blueprint")}
Larbi Gharib's avatar
Larbi Gharib committed
                            </strong>
                            {group.blueprint}
                          </li>
                        </ul>
Larbi Gharib's avatar
Larbi Gharib committed
                    </Link>
Larbi Gharib's avatar
Larbi Gharib committed
                    <CardFooter>
                      <IconButton
Larbi Gharib's avatar
Larbi Gharib committed
                        onClick={() => {
Larbi Gharib's avatar
Larbi Gharib committed
                          handleRemoveGroup(group);
Larbi Gharib's avatar
Larbi Gharib committed
                        }}
Larbi Gharib's avatar
Larbi Gharib committed
                      >
                        <DeleteOutlineIcon />
                      </IconButton>
                    </CardFooter>
                  </Card>
                </GridItem>
              ))
          )}
        </GridContainer>
      </div>
    );
  }