Skip to content

Commit

Permalink
Merge pull request #18 from Abdo9826/hot-fix
Browse files Browse the repository at this point in the history
Add logout button
  • Loading branch information
bobb-Rob authored Nov 4, 2022
2 parents 618aa78 + a6a223f commit ddd97e7
Show file tree
Hide file tree
Showing 17 changed files with 216 additions and 58 deletions.
8 changes: 4 additions & 4 deletions src/components/Reservation/AddReserveForm.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ const AddReserveForm = () => {
const [errorMessages, setErrorMessages] = React.useState([]);

const { cars, reservations } = state;
const { user } = cars;
const { user } = state.user;
const params = useParams();
const currentCar = cars.cars.find((car) => car.id === Number(params.carId)) || {};
const {
Expand All @@ -32,9 +32,9 @@ const AddReserveForm = () => {
const reservation = { ...data, user_id: user.id };
dispatch(createReserve(reservation)).then((response) => {
if (response.type === 'reserve/createReserve/fulfilled') {
if (response.ok) {
if (response.payload.code === 200) {
reset();
navigate('/reservation-list');
navigate('/cars/reservations');
} else {
dispatch(isError(true));
setErrorMessages(response.payload.error);
Expand All @@ -46,7 +46,7 @@ const AddReserveForm = () => {
useEffect(() => () => {
dispatch(addFromNav(false));
dispatch(isError(false));
}, [reservations.addFromNav], dispatch);
}, [reservations.addFromNav, dispatch]);

return (
<div className="container w-75 w-sm-50 mt-5 reserve-form-wrap">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,11 @@ function Reservations() {
<div className="col-md-12">
<h1 className="text-center">Reservations</h1>
<div className="row">
{reservations.length <= 0 && (
<div className="loading">
<h4 className="text-center">No reservations</h4>
</div>
)}
{reservations.map((reservation) => (
<div className="col-md-4" key={reservation.id}>
<div className="card mb-4">
Expand Down
12 changes: 7 additions & 5 deletions src/components/Routing.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import SignUpSuccesPage from './sign-in-sign-up/SignUpSuccesPage';
import CarsPage from './cars/CarsPage';
import Cars from './cars/Cars';
import CarsDetails from './cars/CarsDetails';
import Unauthorized from './sign-in-sign-up/Unauthorized';
import Addcars from './cars/addcars';
import Delete from './cars/delete';
import AddReserveForm from './Reservation/AddReserveForm';
Expand All @@ -16,17 +17,18 @@ const Routing = () => (
<Routes>
<Route path="/" element={<Splash />} />
<Route path="/login" element={<SignInForm />} />
<Route path="/login/redirect" element={<Unauthorized />} />
<Route path="/signup" element={<SignUpForm />} />
<Route path="/signup/success" element={<SignUpSuccesPage />} />
<Route path="/cars" element={<CarsPage />}>
<Route path="" element={<Cars />} />
<Route path=":carId" element={<CarsDetails />} />
<Route path="addcar" element={<Addcars />} />
<Route path=":carId/reservations/add" element={<AddReserveForm />} />
<Route path="choose/reservations/add" element={<AddReserveForm />} />
<Route path="reservations" element={<Reservations />} />
<Route path="delete" element={<Delete />} />
</Route>
<Route path="/cars/:carId/reservations/add" element={<AddReserveForm />} />
<Route path="/cars/choose/reservations/add" element={<AddReserveForm />} />
<Route path="/addcar" element={<Addcars />} />
<Route path="/delete" element={<Delete />} />
<Route path="/reservations" element={<Reservations />} />
<Route path="*" element={<h1>404: Not Found</h1>} />
</Routes>
);
Expand Down
1 change: 0 additions & 1 deletion src/components/cars/Carousel.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ import CarCard from './CarCard';

const Carousel = () => {
const carState = useSelector((state) => state.cars);
console.log(carState.cars);
return (
<Slider
infinite
Expand Down
28 changes: 22 additions & 6 deletions src/components/cars/Cars.js
Original file line number Diff line number Diff line change
@@ -1,22 +1,38 @@
import React from 'react';
import React, { useEffect } from 'react';
import { useSelector } from 'react-redux';
import { Link } from 'react-router-dom';
import { Link, useNavigate } from 'react-router-dom';
import 'slick-carousel/slick/slick.css';
import 'slick-carousel/slick/slick-theme.css';
import CarCard from './CarCard';
import '../../styles/Carousel.css';

const Cars = () => {
const carState = useSelector((state) => state.cars);
const threeCars = carState.cars.slice(0, 3);
console.log(threeCars);
const navigate = useNavigate();
const state = useSelector((state) => state);
const { cars } = state.cars;
const { user } = state;
// const threeCars = cars.slice(0, 3);

useEffect(() => {
if (user.status === 'not-logged-in') {
navigate('/login');
}
if (user.error === 'Unauthorized') {
navigate('/login');
}
}, [user.status, user.error, navigate]);

return (
<div className="main-car-container">
<h1>Latest Models</h1>
<p>Please select a car model</p>
<div className="car-container">
{ carState.cars.map((car) => (
{(cars.length <= 0) && (
<div className="loading">
<h4>No Cars to show, Please add new car</h4>
</div>
)}
{ cars.map((car) => (
<div key={car.id}>
<Link to={`/cars/${car.id}`} className="car-link">
<CarCard
Expand Down
1 change: 0 additions & 1 deletion src/components/cars/addcars.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ function Addcars() {

const onSubmit = (car, e) => {
e.preventDefault();
console.log(car);
dispatch(addcars(car)).then((response) => {
const { code } = response.payload;
if (code === 200) {
Expand Down
18 changes: 14 additions & 4 deletions src/components/navbar/Navbar.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,23 +12,33 @@ import { HiMenu } from 'react-icons/hi';
import '../../styles/navbar.css';
import logo from '../../images/cars-bnb-logo.png';
import { addFromNav } from '../../redux/Reservations/ReserveSlice';
import { logout } from '../../redux/Auth/authenticationSlice';

function Navbar() {
const dispatch = useDispatch();
const carId = useParams().carId || 'choose';

return (
<header className="my-navbar">
<div className="logout">
<button
type="button"
className="logout-btn"
onClick={() => dispatch(logout())}
>
Logout
</button>
</div>
<div className="logo">
<img src={logo} alt="carsBnb Logo" />
</div>
<nav className="menu">
<div className="mobile-nav desktop-nav">
<div className="my-nav-links">
<NavLink to="/cars" className="active">
<NavLink to="/cars">
CARS
</NavLink>
<NavLink to="/addcar">ADD CAR</NavLink>
<NavLink to="addcar">ADD CAR</NavLink>
<NavLink
to={`/cars/${carId}/reservations/add`}
onClick={() => {
Expand All @@ -37,8 +47,8 @@ function Navbar() {
>
RESERVE
</NavLink>
<NavLink to="/reservations">MY RESERVATIONS</NavLink>
<NavLink to="/delete">DELETE CAR</NavLink>
<NavLink to="reservations">MY RESERVATIONS</NavLink>
<NavLink to="delete">DELETE CAR</NavLink>
</div>
<div className="nav-footer">
<div className="nav-icons">
Expand Down
1 change: 0 additions & 1 deletion src/components/sign-in-sign-up/SignUpForm.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@ const SignUpForm = () => {
setIsError(false);
setErrorMessage([]);
dispatch(signUpUser(user)).then((response) => {
console.log(response);
const { code } = response.payload.status;
if (code === 200) {
reset();
Expand Down
11 changes: 11 additions & 0 deletions src/components/sign-in-sign-up/Unauthorized.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import React from 'react';
import { Link } from 'react-router-dom';

const Unauthorized = () => (
<div>
<h1>You need to login to continue</h1>
<Link to="/login">Login</Link>
</div>
);

export default Unauthorized;
2 changes: 2 additions & 0 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { Provider } from 'react-redux';
import store from './redux/store';
import { fetchCars } from './redux/Cars/carSlice';
import { fetchReservations } from './redux/Reservations/ReserveSlice';
import { getUser } from './redux/Auth/authenticationSlice';

import App from './App';
// Bootstrap CSS
Expand All @@ -18,6 +19,7 @@ const root = createRoot(container);

store.dispatch(fetchCars());
store.dispatch(fetchReservations());
store.dispatch(getUser());

root.render(
<BrowserRouter>
Expand Down
129 changes: 106 additions & 23 deletions src/redux/Auth/authenticationSlice.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,31 @@
import { createAsyncThunk, createSlice, current } from '@reduxjs/toolkit';
import setJwtToken from './saveJwtToken';

export const getUser = createAsyncThunk(
'user/getUser',
async (_, { rejectWithValue }) => {
try {
const token = localStorage.getItem('loginToken');
const url = 'http://localhost:3001/current_user';
const options = {
method: 'GET',
headers: {
'Content-Type': 'application/json',
Authorization: token,
},
};
const response = await fetch(url, options);
if (response.status === 401) {
return rejectWithValue('Unauthorized');
}
const data = await response.json();
return data;
} catch (err) {
return rejectWithValue(err);
}
},
);

export const signUpUser = createAsyncThunk(
'authentication/signUpUser',
async (user, { rejectWithValue }) => {
Expand Down Expand Up @@ -41,44 +66,102 @@ export const signInUser = createAsyncThunk(
},
);

export const logout = createAsyncThunk(
'authentication/logout',
async (_, { rejectWithValue }) => {
try {
const token = localStorage.getItem('loginToken');
const response = await fetch('http://localhost:3001/users/sign_out', {
method: 'DELETE',
headers: {
'Content-Type': 'application/json',
Authorization: token,
},
});
const data = await response.json();
return data;
} catch (err) {
return rejectWithValue(err);
}
},
);

const initialState = {
name: '',
email: '',
password: '',
user: {
name: '',
email: '',
password: '',
},
status: 'idle',
error: null,
};

const authenticationSlice = createSlice({
name: 'user',
initialState,
reducers: {},
reducers: {
clearUser(state) {
const newState = { ...current(state) };
newState.user = {
name: '',
email: '',
password: '',
};
newState.error = null;
newState.status = 'idle';
return newState;
},
},
extraReducers: {
[signUpUser.fulfilled]: (state, action) => {
const {
admin, email, id, name,
} = action.payload.status.data;
const newState = {
...current(state),
name,
email,
id,
admin,
};
const newState = { ...current(state) };
newState.user = action.payload.status.data;
newState.status = action.payload.message;
return newState;
},
[signUpUser.rejected]: (state, action) => {
const newState = { ...current(state) };
newState.error = action.payload;
newState.status = 'failed';
return newState;
},
[signInUser.fulfilled]: (state, action) => {
const {
admin, email, id, name,
} = action.payload.user;
const newState = {
...current(state),
name,
email,
id,
admin,
const newState = { ...current(state) };
newState.user = action.payload.user;
newState.status = 'logged-in';
newState.error = null;
return newState;
},
[signInUser.rejected]: (state, action) => {
const newState = { ...current(state) };
newState.error = action.payload;
newState.status = 'failed';
return newState;
},
[logout.fulfilled]: (state) => {
const newState = { ...current(state) };
newState.user = {
name: '',
email: '',
password: '',
};
newState.status = 'not-logged-in';
return newState;
},
[getUser.fulfilled]: (state, action) => {
const newState = { ...current(state) };
newState.user = action.payload;
newState.status = 'logged-in';
return newState;
},
[getUser.rejected]: (state, action) => {
const newState = { ...current(state) };
newState.error = action.payload;
newState.status = 'failed';
return newState;
},
},
});

export default authenticationSlice.reducer;
export const { clearUser } = authenticationSlice.actions;
1 change: 0 additions & 1 deletion src/redux/Cars/addcarSlice.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ const addcars = createAsyncThunk(
async (car, { rejectWithValue }) => {
try {
const token = localStorage.getItem('loginToken');
console.log(token);
const response = await fetch('http://localhost:3001/cars', {
method: 'POST',
headers: {
Expand Down
3 changes: 2 additions & 1 deletion src/redux/Cars/carSlice.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,8 @@ const carSlice = createSlice({
},
[addcars.fulfilled]: (state, action) => {
const newState = { ...current(state) };
newState.cars.push(action.payload.car);
newState.cars = [...newState.cars, action.payload.car];
newState.status = action.payload.notice;
return newState;
},
[deleteCars.fulfilled]: (state, action) => {
Expand Down
Loading

0 comments on commit ddd97e7

Please sign in to comment.