refactor: clean up components
This commit is contained in:
		
							
								
								
									
										35
									
								
								frontend/src/App/Toast.ts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										35
									
								
								frontend/src/App/Toast.ts
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,35 @@
 | 
				
			|||||||
 | 
					import styled from 'styled-components';
 | 
				
			||||||
 | 
					import { ToastContainer } from 'react-toastify';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const ToastedContainer = styled(ToastContainer).attrs({
 | 
				
			||||||
 | 
					  // custom props
 | 
				
			||||||
 | 
					})`
 | 
				
			||||||
 | 
					  .Toastify__toast-container {
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__toast {
 | 
				
			||||||
 | 
					    padding: 5px;
 | 
				
			||||||
 | 
					    margin-left: 5px;
 | 
				
			||||||
 | 
					    margin-right: 5px;
 | 
				
			||||||
 | 
					    border-radius: 10px;
 | 
				
			||||||
 | 
					    background: #7367f0;
 | 
				
			||||||
 | 
					    color: #fff;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__toast--error {
 | 
				
			||||||
 | 
					    background: ${props => props.theme.colors.danger};
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__toast--warning {
 | 
				
			||||||
 | 
					    background: ${props => props.theme.colors.warning};
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__toast--success {
 | 
				
			||||||
 | 
					    background: ${props => props.theme.colors.success};
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__toast-body {
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__progress-bar {
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  .Toastify__close-button {
 | 
				
			||||||
 | 
					    display: none;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					`;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export default ToastedContainer;
 | 
				
			||||||
@@ -1,16 +1,13 @@
 | 
				
			|||||||
import React, { useState, useRef, useEffect } from 'react';
 | 
					import React, { useState } from 'react';
 | 
				
			||||||
import styled from 'styled-components/macro';
 | 
					import styled from 'styled-components/macro';
 | 
				
			||||||
import { useGetProjectsQuery } from 'shared/generated/graphql';
 | 
					import { useGetProjectsQuery } from 'shared/generated/graphql';
 | 
				
			||||||
import { Link } from 'react-router-dom';
 | 
					import { Link } from 'react-router-dom';
 | 
				
			||||||
import LoadingSpinner from 'shared/components/LoadingSpinner';
 | 
					import LoadingSpinner from 'shared/components/LoadingSpinner';
 | 
				
			||||||
import theme from './ThemeStyles';
 | 
					 | 
				
			||||||
import ControlledInput from 'shared/components/ControlledInput';
 | 
					import ControlledInput from 'shared/components/ControlledInput';
 | 
				
			||||||
import { CaretDown, CaretRight } from 'shared/icons';
 | 
					import { CaretDown, CaretRight } from 'shared/icons';
 | 
				
			||||||
import useStickyState from 'shared/hooks/useStickyState';
 | 
					import useStickyState from 'shared/hooks/useStickyState';
 | 
				
			||||||
import { usePopup } from 'shared/components/PopupMenu';
 | 
					import { usePopup } from 'shared/components/PopupMenu';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const colors = [theme.colors.primary, theme.colors.secondary];
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
const TeamContainer = styled.div`
 | 
					const TeamContainer = styled.div`
 | 
				
			||||||
  display: flex;
 | 
					  display: flex;
 | 
				
			||||||
  flex-direction: column;
 | 
					  flex-direction: column;
 | 
				
			||||||
@@ -27,6 +24,7 @@ const TeamTitleText = styled.span`
 | 
				
			|||||||
  font-size: 14px;
 | 
					  font-size: 14px;
 | 
				
			||||||
  font-weight: 700;
 | 
					  font-weight: 700;
 | 
				
			||||||
`;
 | 
					`;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const TeamProjects = styled.div`
 | 
					const TeamProjects = styled.div`
 | 
				
			||||||
  display: flex;
 | 
					  display: flex;
 | 
				
			||||||
  flex-direction: column;
 | 
					  flex-direction: column;
 | 
				
			||||||
							
								
								
									
										61
									
								
								frontend/src/App/TopNavbar/ProjectPopup.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										61
									
								
								frontend/src/App/TopNavbar/ProjectPopup.tsx
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,61 @@
 | 
				
			|||||||
 | 
					import React from 'react';
 | 
				
			||||||
 | 
					import ProjectSettings, { DeleteConfirm, DELETE_INFO } from 'shared/components/ProjectSettings';
 | 
				
			||||||
 | 
					import { useDeleteProjectMutation, GetProjectsDocument } from 'shared/generated/graphql';
 | 
				
			||||||
 | 
					import { usePopup, Popup } from 'shared/components/PopupMenu';
 | 
				
			||||||
 | 
					import produce from 'immer';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					type ProjectPopupProps = {
 | 
				
			||||||
 | 
					  history: any;
 | 
				
			||||||
 | 
					  name: string;
 | 
				
			||||||
 | 
					  projectID: string;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const ProjectPopup: React.FC<ProjectPopupProps> = ({ history, name, projectID }) => {
 | 
				
			||||||
 | 
					  const { hidePopup, setTab } = usePopup();
 | 
				
			||||||
 | 
					  const [deleteProject] = useDeleteProjectMutation({
 | 
				
			||||||
 | 
					    update: (client, deleteData) => {
 | 
				
			||||||
 | 
					      const cacheData: any = client.readQuery({
 | 
				
			||||||
 | 
					        query: GetProjectsDocument,
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      const newData = produce(cacheData, (draftState: any) => {
 | 
				
			||||||
 | 
					        draftState.projects = draftState.projects.filter(
 | 
				
			||||||
 | 
					          (project: any) => project.id !== deleteData.data?.deleteProject.project.id,
 | 
				
			||||||
 | 
					        );
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      client.writeQuery({
 | 
				
			||||||
 | 
					        query: GetProjectsDocument,
 | 
				
			||||||
 | 
					        data: {
 | 
				
			||||||
 | 
					          ...newData,
 | 
				
			||||||
 | 
					        },
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    },
 | 
				
			||||||
 | 
					  });
 | 
				
			||||||
 | 
					  return (
 | 
				
			||||||
 | 
					    <>
 | 
				
			||||||
 | 
					      <Popup title={null} tab={0}>
 | 
				
			||||||
 | 
					        <ProjectSettings
 | 
				
			||||||
 | 
					          onDeleteProject={() => {
 | 
				
			||||||
 | 
					            setTab(1, { width: 300 });
 | 
				
			||||||
 | 
					          }}
 | 
				
			||||||
 | 
					        />
 | 
				
			||||||
 | 
					      </Popup>
 | 
				
			||||||
 | 
					      <Popup title={`Delete the "${name}" project?`} tab={1}>
 | 
				
			||||||
 | 
					        <DeleteConfirm
 | 
				
			||||||
 | 
					          description={DELETE_INFO.DELETE_PROJECTS.description}
 | 
				
			||||||
 | 
					          deletedItems={DELETE_INFO.DELETE_PROJECTS.deletedItems}
 | 
				
			||||||
 | 
					          onConfirmDelete={() => {
 | 
				
			||||||
 | 
					            if (projectID) {
 | 
				
			||||||
 | 
					              deleteProject({ variables: { projectID } });
 | 
				
			||||||
 | 
					              hidePopup();
 | 
				
			||||||
 | 
					              history.push('/projects');
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					          }}
 | 
				
			||||||
 | 
					        />
 | 
				
			||||||
 | 
					      </Popup>
 | 
				
			||||||
 | 
					    </>
 | 
				
			||||||
 | 
					  );
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export default ProjectPopup;
 | 
				
			||||||
@@ -1,72 +1,16 @@
 | 
				
			|||||||
import React from 'react';
 | 
					import React from 'react';
 | 
				
			||||||
import TopNavbar, { MenuItem } from 'shared/components/TopNavbar';
 | 
					import TopNavbar, { MenuItem } from 'shared/components/TopNavbar';
 | 
				
			||||||
import { ProfileMenu } from 'shared/components/DropdownMenu';
 | 
					import { ProfileMenu } from 'shared/components/DropdownMenu';
 | 
				
			||||||
import ProjectSettings, { DeleteConfirm, DELETE_INFO } from 'shared/components/ProjectSettings';
 | 
					 | 
				
			||||||
import { useHistory } from 'react-router';
 | 
					import { useHistory } from 'react-router';
 | 
				
			||||||
import { useCurrentUser } from 'App/context';
 | 
					import { useCurrentUser } from 'App/context';
 | 
				
			||||||
import { RoleCode, useTopNavbarQuery, useDeleteProjectMutation, GetProjectsDocument } from 'shared/generated/graphql';
 | 
					import { RoleCode, useTopNavbarQuery } from 'shared/generated/graphql';
 | 
				
			||||||
import { usePopup, Popup } from 'shared/components/PopupMenu';
 | 
					import { usePopup, Popup } from 'shared/components/PopupMenu';
 | 
				
			||||||
import produce from 'immer';
 | 
					 | 
				
			||||||
import MiniProfile from 'shared/components/MiniProfile';
 | 
					import MiniProfile from 'shared/components/MiniProfile';
 | 
				
			||||||
import cache from 'App/cache';
 | 
					import cache from 'App/cache';
 | 
				
			||||||
import NotificationPopup, { NotificationItem } from 'shared/components/NotifcationPopup';
 | 
					import NotificationPopup, { NotificationItem } from 'shared/components/NotifcationPopup';
 | 
				
			||||||
import theme from './ThemeStyles';
 | 
					import theme from 'App/ThemeStyles';
 | 
				
			||||||
import ProjectFinder from './ProjectFinder';
 | 
					import ProjectFinder from './ProjectFinder';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
type ProjectPopupProps = {
 | 
					 | 
				
			||||||
  history: any;
 | 
					 | 
				
			||||||
  name: string;
 | 
					 | 
				
			||||||
  projectID: string;
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
export const ProjectPopup: React.FC<ProjectPopupProps> = ({ history, name, projectID }) => {
 | 
					 | 
				
			||||||
  const { hidePopup, setTab } = usePopup();
 | 
					 | 
				
			||||||
  const [deleteProject] = useDeleteProjectMutation({
 | 
					 | 
				
			||||||
    update: (client, deleteData) => {
 | 
					 | 
				
			||||||
      const cacheData: any = client.readQuery({
 | 
					 | 
				
			||||||
        query: GetProjectsDocument,
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
      const newData = produce(cacheData, (draftState: any) => {
 | 
					 | 
				
			||||||
        draftState.projects = draftState.projects.filter(
 | 
					 | 
				
			||||||
          (project: any) => project.id !== deleteData.data?.deleteProject.project.id,
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
      client.writeQuery({
 | 
					 | 
				
			||||||
        query: GetProjectsDocument,
 | 
					 | 
				
			||||||
        data: {
 | 
					 | 
				
			||||||
          ...newData,
 | 
					 | 
				
			||||||
        },
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
    },
 | 
					 | 
				
			||||||
  });
 | 
					 | 
				
			||||||
  return (
 | 
					 | 
				
			||||||
    <>
 | 
					 | 
				
			||||||
      <Popup title={null} tab={0}>
 | 
					 | 
				
			||||||
        <ProjectSettings
 | 
					 | 
				
			||||||
          onDeleteProject={() => {
 | 
					 | 
				
			||||||
            setTab(1, { width: 300 });
 | 
					 | 
				
			||||||
          }}
 | 
					 | 
				
			||||||
        />
 | 
					 | 
				
			||||||
      </Popup>
 | 
					 | 
				
			||||||
      <Popup title={`Delete the "${name}" project?`} tab={1}>
 | 
					 | 
				
			||||||
        <DeleteConfirm
 | 
					 | 
				
			||||||
          description={DELETE_INFO.DELETE_PROJECTS.description}
 | 
					 | 
				
			||||||
          deletedItems={DELETE_INFO.DELETE_PROJECTS.deletedItems}
 | 
					 | 
				
			||||||
          onConfirmDelete={() => {
 | 
					 | 
				
			||||||
            if (projectID) {
 | 
					 | 
				
			||||||
              deleteProject({ variables: { projectID } });
 | 
					 | 
				
			||||||
              hidePopup();
 | 
					 | 
				
			||||||
              history.push('/projects');
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
          }}
 | 
					 | 
				
			||||||
        />
 | 
					 | 
				
			||||||
      </Popup>
 | 
					 | 
				
			||||||
    </>
 | 
					 | 
				
			||||||
  );
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
type GlobalTopNavbarProps = {
 | 
					type GlobalTopNavbarProps = {
 | 
				
			||||||
  nameOnly?: boolean;
 | 
					  nameOnly?: boolean;
 | 
				
			||||||
  projectID: string | null;
 | 
					  projectID: string | null;
 | 
				
			||||||
@@ -103,10 +47,7 @@ const GlobalTopNavbar: React.FC<GlobalTopNavbarProps> = ({
 | 
				
			|||||||
  onRemoveFromBoard,
 | 
					  onRemoveFromBoard,
 | 
				
			||||||
}) => {
 | 
					}) => {
 | 
				
			||||||
  const { user, setUser } = useCurrentUser();
 | 
					  const { user, setUser } = useCurrentUser();
 | 
				
			||||||
  const { loading, data } = useTopNavbarQuery({
 | 
					  const { data } = useTopNavbarQuery();
 | 
				
			||||||
    // TODO: maybe remove?
 | 
					 | 
				
			||||||
    onCompleted: response => {},
 | 
					 | 
				
			||||||
  });
 | 
					 | 
				
			||||||
  const { showPopup, hidePopup } = usePopup();
 | 
					  const { showPopup, hidePopup } = usePopup();
 | 
				
			||||||
  const history = useHistory();
 | 
					  const history = useHistory();
 | 
				
			||||||
  const onLogout = () => {
 | 
					  const onLogout = () => {
 | 
				
			||||||
@@ -129,7 +70,7 @@ const GlobalTopNavbar: React.FC<GlobalTopNavbarProps> = ({
 | 
				
			|||||||
      <Popup title={null} tab={0}>
 | 
					      <Popup title={null} tab={0}>
 | 
				
			||||||
        <ProfileMenu
 | 
					        <ProfileMenu
 | 
				
			||||||
          onLogout={onLogout}
 | 
					          onLogout={onLogout}
 | 
				
			||||||
          showAdminConsole={true} // TODO: add permision check
 | 
					          showAdminConsole // TODO: add permision check
 | 
				
			||||||
          onAdminConsole={() => {
 | 
					          onAdminConsole={() => {
 | 
				
			||||||
            history.push('/admin');
 | 
					            history.push('/admin');
 | 
				
			||||||
            hidePopup();
 | 
					            hidePopup();
 | 
				
			||||||
@@ -2,47 +2,16 @@ import React, { useState, useEffect } from 'react';
 | 
				
			|||||||
import { createBrowserHistory } from 'history';
 | 
					import { createBrowserHistory } from 'history';
 | 
				
			||||||
import { Router } from 'react-router';
 | 
					import { Router } from 'react-router';
 | 
				
			||||||
import { PopupProvider } from 'shared/components/PopupMenu';
 | 
					import { PopupProvider } from 'shared/components/PopupMenu';
 | 
				
			||||||
import { ToastContainer } from 'react-toastify';
 | 
					 | 
				
			||||||
import styled, { ThemeProvider } from 'styled-components';
 | 
					import styled, { ThemeProvider } from 'styled-components';
 | 
				
			||||||
import NormalizeStyles from './NormalizeStyles';
 | 
					import NormalizeStyles from './NormalizeStyles';
 | 
				
			||||||
import BaseStyles from './BaseStyles';
 | 
					import BaseStyles from './BaseStyles';
 | 
				
			||||||
import theme from './ThemeStyles';
 | 
					import theme from './ThemeStyles';
 | 
				
			||||||
import Routes from './Routes';
 | 
					import Routes from './Routes';
 | 
				
			||||||
 | 
					import ToastedContainer from './Toast';
 | 
				
			||||||
import { UserContext } from './context';
 | 
					import { UserContext } from './context';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import 'react-toastify/dist/ReactToastify.css';
 | 
					import 'react-toastify/dist/ReactToastify.css';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const StyledContainer = styled(ToastContainer).attrs({
 | 
					 | 
				
			||||||
  // custom props
 | 
					 | 
				
			||||||
})`
 | 
					 | 
				
			||||||
  .Toastify__toast-container {
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__toast {
 | 
					 | 
				
			||||||
    padding: 5px;
 | 
					 | 
				
			||||||
    margin-left: 5px;
 | 
					 | 
				
			||||||
    margin-right: 5px;
 | 
					 | 
				
			||||||
    border-radius: 10px;
 | 
					 | 
				
			||||||
    background: #7367f0;
 | 
					 | 
				
			||||||
    color: #fff;
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__toast--error {
 | 
					 | 
				
			||||||
    background: ${props => props.theme.colors.danger};
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__toast--warning {
 | 
					 | 
				
			||||||
    background: ${props => props.theme.colors.warning};
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__toast--success {
 | 
					 | 
				
			||||||
    background: ${props => props.theme.colors.success};
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__toast-body {
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__progress-bar {
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  .Toastify__close-button {
 | 
					 | 
				
			||||||
    display: none;
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
`;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
const history = createBrowserHistory();
 | 
					const history = createBrowserHistory();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const App = () => {
 | 
					const App = () => {
 | 
				
			||||||
@@ -59,7 +28,7 @@ const App = () => {
 | 
				
			|||||||
              <Routes history={history} />
 | 
					              <Routes history={history} />
 | 
				
			||||||
            </PopupProvider>
 | 
					            </PopupProvider>
 | 
				
			||||||
          </Router>
 | 
					          </Router>
 | 
				
			||||||
          <StyledContainer
 | 
					          <ToastedContainer
 | 
				
			||||||
            position="bottom-right"
 | 
					            position="bottom-right"
 | 
				
			||||||
            autoClose={5000}
 | 
					            autoClose={5000}
 | 
				
			||||||
            hideProgressBar
 | 
					            hideProgressBar
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,16 +1,13 @@
 | 
				
			|||||||
import React, { useState } from 'react';
 | 
					import React from 'react';
 | 
				
			||||||
import axios from 'axios';
 | 
					 | 
				
			||||||
import Confirm from 'shared/components/Confirm';
 | 
					import Confirm from 'shared/components/Confirm';
 | 
				
			||||||
import { useHistory, useLocation } from 'react-router';
 | 
					import { useHistory, useLocation } from 'react-router';
 | 
				
			||||||
import * as QueryString from 'query-string';
 | 
					import * as QueryString from 'query-string';
 | 
				
			||||||
import { toast } from 'react-toastify';
 | 
					 | 
				
			||||||
import { Container, LoginWrapper } from './Styles';
 | 
					 | 
				
			||||||
import { useCurrentUser } from 'App/context';
 | 
					import { useCurrentUser } from 'App/context';
 | 
				
			||||||
 | 
					import { Container, LoginWrapper } from './Styles';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const UsersConfirm = () => {
 | 
					const UsersConfirm = () => {
 | 
				
			||||||
  const history = useHistory();
 | 
					  const history = useHistory();
 | 
				
			||||||
  const location = useLocation();
 | 
					  const location = useLocation();
 | 
				
			||||||
  const [registered, setRegistered] = useState(false);
 | 
					 | 
				
			||||||
  const params = QueryString.parse(location.search);
 | 
					  const params = QueryString.parse(location.search);
 | 
				
			||||||
  const { setUser } = useCurrentUser();
 | 
					  const { setUser } = useCurrentUser();
 | 
				
			||||||
  return (
 | 
					  return (
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user