Implement public/private routing
This commit is contained in:
parent
125a03f529
commit
ec65c3b9dd
32
src/App.js
Normal file
32
src/App.js
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
import React from 'react';
|
||||||
|
import 'rsuite/lib/styles/index.less';
|
||||||
|
import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';
|
||||||
|
|
||||||
|
import PrivateRoute from './components/routes/PrivateRoute';
|
||||||
|
import PublicRoute from './components/routes/PublicRoute';
|
||||||
|
|
||||||
|
import Dashboard from './screens/Dashboard';
|
||||||
|
import Schedule from './screens/Schedule/Schedule';
|
||||||
|
import Availability from './screens/Availability/Availability';
|
||||||
|
import Invite from './screens/Invite/Invite';
|
||||||
|
import Login from './screens/Login';
|
||||||
|
import Register from './screens/Register';
|
||||||
|
|
||||||
|
export default function App() {
|
||||||
|
return (
|
||||||
|
<Router>
|
||||||
|
<Switch>
|
||||||
|
<Route path='/' exact component={Login} />
|
||||||
|
|
||||||
|
<PublicRoute path='/login' component={Login} />
|
||||||
|
<PublicRoute path='/register' component={Register} />
|
||||||
|
|
||||||
|
<PrivateRoute path='/dashboard' component={Dashboard} />
|
||||||
|
<PrivateRoute path='/schedule' component={Schedule} />
|
||||||
|
<PrivateRoute path='/invite' component={Invite} />
|
||||||
|
<PrivateRoute path='/availability' component={Availability} />
|
||||||
|
<PrivateRoute path='/schedule' component={Schedule} />
|
||||||
|
</Switch>
|
||||||
|
</Router>
|
||||||
|
);
|
||||||
|
}
|
@ -2,10 +2,9 @@ import React from 'react';
|
|||||||
import { Helmet } from 'react-helmet';
|
import { Helmet } from 'react-helmet';
|
||||||
|
|
||||||
export default function TitleComponent({ title }) {
|
export default function TitleComponent({ title }) {
|
||||||
var defaultTitle = 'Meeting Planner';
|
|
||||||
return (
|
return (
|
||||||
<Helmet>
|
<Helmet>
|
||||||
<title>{title ? `${title} | Meeting Planner` : defaultTitle}</title>
|
<title>{title ? `${title} | Meeting Planner` : 'Meeting Planner'}</title>
|
||||||
</Helmet>
|
</Helmet>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -16,13 +16,11 @@ export default function NavBar({ title }) {
|
|||||||
alignItems: 'center',
|
alignItems: 'center',
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Nav style={{ visibility: 'hidden' }}>
|
|
||||||
{/* This hidden nav is a hack to have the title perfectly centered. */}
|
{/* This hidden nav is a hack to have the title perfectly centered. */}
|
||||||
|
<Nav style={{ visibility: 'hidden' }}>
|
||||||
<MenuDropdown />
|
<MenuDropdown />
|
||||||
</Nav>
|
</Nav>
|
||||||
<div>
|
|
||||||
<h3>{title}</h3>
|
<h3>{title}</h3>
|
||||||
</div>
|
|
||||||
<MenuDropdown />
|
<MenuDropdown />
|
||||||
</Navbar.Body>
|
</Navbar.Body>
|
||||||
</Navbar>
|
</Navbar>
|
||||||
|
29
src/components/routes/PrivateRoute.js
Normal file
29
src/components/routes/PrivateRoute.js
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
import React from 'react';
|
||||||
|
import { Route, Redirect } from 'react-router-dom';
|
||||||
|
import { getToken } from '../../utils/common';
|
||||||
|
|
||||||
|
const isLoggedIn = getToken();
|
||||||
|
|
||||||
|
const PrivateRoute = ({ component: Component, user, ...rest }) => {
|
||||||
|
return (
|
||||||
|
<Route
|
||||||
|
{...rest}
|
||||||
|
render={(props) =>
|
||||||
|
isLoggedIn ? (
|
||||||
|
<Component {...rest} {...props} />
|
||||||
|
) : (
|
||||||
|
<Redirect
|
||||||
|
to={{
|
||||||
|
pathname: '/login',
|
||||||
|
state: {
|
||||||
|
from: props.location,
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default PrivateRoute;
|
22
src/components/routes/PublicRoute.js
Normal file
22
src/components/routes/PublicRoute.js
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
import React from 'react';
|
||||||
|
import { Route, Redirect } from 'react-router-dom';
|
||||||
|
import { getToken } from '../../utils/common';
|
||||||
|
|
||||||
|
const isLoggedIn = getToken();
|
||||||
|
|
||||||
|
function PublicRoute({ component: Component, ...rest }) {
|
||||||
|
return (
|
||||||
|
<Route
|
||||||
|
{...rest}
|
||||||
|
render={(props) =>
|
||||||
|
!isLoggedIn ? (
|
||||||
|
<Component {...props} />
|
||||||
|
) : (
|
||||||
|
<Redirect to={{ pathname: '/dashboard' }} />
|
||||||
|
)
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export default PublicRoute;
|
@ -1,6 +1,6 @@
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { render } from 'react-dom';
|
import { render } from 'react-dom';
|
||||||
import App from './screens/App';
|
import App from './App';
|
||||||
|
|
||||||
import 'rsuite/lib/styles/index.less';
|
import 'rsuite/lib/styles/index.less';
|
||||||
|
|
||||||
|
@ -1,51 +0,0 @@
|
|||||||
import React from 'react';
|
|
||||||
import 'rsuite/lib/styles/index.less';
|
|
||||||
import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';
|
|
||||||
|
|
||||||
import Dashboard from './Dashboard';
|
|
||||||
import Schedule from './Schedule/Schedule';
|
|
||||||
import Availability from './Availability/Availability';
|
|
||||||
import Invite from './Invite/Invite';
|
|
||||||
import Login from './Login';
|
|
||||||
import Register from './Register';
|
|
||||||
|
|
||||||
const titles = {
|
|
||||||
schedule: 'Schedule a meeting',
|
|
||||||
invite: 'Invite participants',
|
|
||||||
availability: 'Add your availability',
|
|
||||||
confirm: 'Confirm meeting date',
|
|
||||||
dashboard: 'Dashboard',
|
|
||||||
login: 'Login',
|
|
||||||
register: 'Register',
|
|
||||||
settings: 'Settings',
|
|
||||||
};
|
|
||||||
|
|
||||||
export default function App() {
|
|
||||||
return (
|
|
||||||
<Router>
|
|
||||||
<Switch>
|
|
||||||
<Route path='/' exact>
|
|
||||||
<Login title={titles.login} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/schedule'>
|
|
||||||
<Schedule title={titles.schedule} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/invite'>
|
|
||||||
<Invite title={titles.invite} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/availability'>
|
|
||||||
<Availability title={titles.availability} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/dashboard'>
|
|
||||||
<Dashboard title={titles.dashboard} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/login'>
|
|
||||||
<Login title={titles.login} />
|
|
||||||
</Route>
|
|
||||||
<Route path='/register'>
|
|
||||||
<Register title={titles.register} />
|
|
||||||
</Route>
|
|
||||||
</Switch>
|
|
||||||
</Router>
|
|
||||||
);
|
|
||||||
}
|
|
@ -17,7 +17,7 @@ import IntervalSelector from '../../components/Interval/IntervalSelector';
|
|||||||
|
|
||||||
import './Availability.less';
|
import './Availability.less';
|
||||||
|
|
||||||
export default function Availability({ title }) {
|
export default function Availability() {
|
||||||
const [availability, setAvailability] = useState([...availabilityList]);
|
const [availability, setAvailability] = useState([...availabilityList]);
|
||||||
|
|
||||||
const handleClear = () => {
|
const handleClear = () => {
|
||||||
@ -36,7 +36,7 @@ export default function Availability({ title }) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<NavBar title={title} />
|
<NavBar title='Add your availability' />
|
||||||
<Panel style={containerStyle}>
|
<Panel style={containerStyle}>
|
||||||
<Form className={'av-container'}>
|
<Form className={'av-container'}>
|
||||||
<div className={'av-details'}>
|
<div className={'av-details'}>
|
||||||
|
@ -6,7 +6,7 @@ import { Panel, Form, Button, ButtonGroup, Message, TagPicker } from 'rsuite';
|
|||||||
import NavBar from '../../components/Navbar/NavBar';
|
import NavBar from '../../components/Navbar/NavBar';
|
||||||
import './Invite.less';
|
import './Invite.less';
|
||||||
|
|
||||||
export default function Invite({ title }) {
|
export default function Invite() {
|
||||||
const [participants, setParticipants] = useState([]);
|
const [participants, setParticipants] = useState([]);
|
||||||
const [contactDropdown, setContactDropdown] = useState([]);
|
const [contactDropdown, setContactDropdown] = useState([]);
|
||||||
|
|
||||||
@ -63,7 +63,7 @@ export default function Invite({ title }) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<NavBar title={title} />
|
<NavBar title='Invite participants' />
|
||||||
<Panel style={containerStyle}>
|
<Panel style={containerStyle}>
|
||||||
<Form className={'av-container'}>
|
<Form className={'av-container'}>
|
||||||
<div className={'interval-selector'}>
|
<div className={'interval-selector'}>
|
||||||
|
@ -14,7 +14,7 @@ import {
|
|||||||
import { setUserSession } from '../utils/common';
|
import { setUserSession } from '../utils/common';
|
||||||
import NavBar from './../components/Navbar/NavBar';
|
import NavBar from './../components/Navbar/NavBar';
|
||||||
|
|
||||||
export default function Login({ title }) {
|
export default function Login() {
|
||||||
const history = useHistory();
|
const history = useHistory();
|
||||||
|
|
||||||
const [error, setError] = useState(false);
|
const [error, setError] = useState(false);
|
||||||
@ -46,7 +46,7 @@ export default function Login({ title }) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<NavBar title={title} />
|
<NavBar title='Login' />
|
||||||
<Panel bordered style={boxStyle}>
|
<Panel bordered style={boxStyle}>
|
||||||
{error && <Message type='error' description={error} />}
|
{error && <Message type='error' description={error} />}
|
||||||
<Form>
|
<Form>
|
||||||
|
@ -16,10 +16,10 @@ const boxStyle = {
|
|||||||
padding: '1rem',
|
padding: '1rem',
|
||||||
};
|
};
|
||||||
|
|
||||||
export default function Register({ title }) {
|
export default function Register() {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<NavBar title={title} />
|
<NavBar title='Register' />
|
||||||
<Panel bordered style={boxStyle}>
|
<Panel bordered style={boxStyle}>
|
||||||
<Form>
|
<Form>
|
||||||
<FormGroup>
|
<FormGroup>
|
||||||
|
@ -21,7 +21,7 @@ import SelectedDates from '../../components/Schedule/SelectedDates';
|
|||||||
|
|
||||||
import './Schedule.less';
|
import './Schedule.less';
|
||||||
|
|
||||||
export default function Schedule({ title }) {
|
export default function Schedule() {
|
||||||
const [eventsList, setEventsList] = useState([]);
|
const [eventsList, setEventsList] = useState([]);
|
||||||
const [datesList, setDatesList] = useState(eventsToDates(eventsList));
|
const [datesList, setDatesList] = useState(eventsToDates(eventsList));
|
||||||
|
|
||||||
@ -117,7 +117,7 @@ export default function Schedule({ title }) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<NavBar title={title} />
|
<NavBar title='Schedule a meeting' />
|
||||||
<Panel style={containerStyle}>
|
<Panel style={containerStyle}>
|
||||||
<Form className={'meeting-container'}>
|
<Form className={'meeting-container'}>
|
||||||
<div className={'meeting-info'}>
|
<div className={'meeting-info'}>
|
||||||
|
@ -1,27 +1,26 @@
|
|||||||
// return the user data from the local storage
|
// Set/Remove user and token to local storage
|
||||||
export const getUser = () => {
|
export const setUserSession = (token, user) => {
|
||||||
const user = JSON.parse(localStorage.getItem('user'));
|
localStorage.setItem('token', token);
|
||||||
|
localStorage.setItem('user', JSON.stringify(user));
|
||||||
if (user) return user;
|
};
|
||||||
else return null;
|
|
||||||
|
export const getUser = () => {
|
||||||
|
const userJSON = localStorage.getItem('user');
|
||||||
|
|
||||||
|
if (userJSON) {
|
||||||
|
const user = JSON.parse(userJSON);
|
||||||
|
return user;
|
||||||
|
} else return null;
|
||||||
};
|
};
|
||||||
|
|
||||||
// return the token from the local storage
|
|
||||||
export const getToken = () => {
|
export const getToken = () => {
|
||||||
const token = JSON.parse(localStorage.getItem('token'));
|
const token = localStorage.getItem('token');
|
||||||
|
|
||||||
if (token) return token;
|
if (token) return token;
|
||||||
else return null;
|
else return null;
|
||||||
};
|
};
|
||||||
|
|
||||||
// remove the token and user from the local storage
|
|
||||||
export const removeUserSession = () => {
|
export const removeUserSession = () => {
|
||||||
localStorage.removeItem('token');
|
localStorage.removeItem('token');
|
||||||
localStorage.removeItem('user');
|
localStorage.removeItem('user');
|
||||||
};
|
};
|
||||||
|
|
||||||
// set the token and user from the local storage
|
|
||||||
export const setUserSession = (token, user) => {
|
|
||||||
localStorage.setItem('token', token);
|
|
||||||
localStorage.setItem('user', JSON.stringify(user));
|
|
||||||
};
|
|
||||||
|
Loading…
Reference in New Issue
Block a user