Skip to content

Commit

Permalink
➖ Change the cookies dependency & depend on the local storage to stor…
Browse files Browse the repository at this point in the history
…e the user data & tokens instead
  • Loading branch information
Mohamed-Elhawary committed Oct 23, 2021
1 parent 795ebcb commit 74704c4
Show file tree
Hide file tree
Showing 14 changed files with 53 additions and 76 deletions.
19 changes: 10 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ https://user-images.githubusercontent.com/69651552/138542024-937ee1bd-c31c-435b-
* [React Router Dom](https://www.npmjs.com/package/react-router-dom)
* [Styled Components](https://styled-components.com/)
* [Axios](https://www.npmjs.com/package/axios)
* [Js Cookie](https://www.npmjs.com/package/js-cookie)
* [React Icons](https://react-icons.github.io/react-icons/)
* [React Slick](https://www.npmjs.com/package/react-slick)
* [React Youtube](https://www.npmjs.com/package/react-youtube)
Expand Down Expand Up @@ -97,25 +96,27 @@ Feel Free to Deploy it with me, send Issues or a Pull Request and i'll deal with

1- The App has a Simulation for the Authentication process, so you have to enter any username and any password from you choice in the login form to be able to see the home screen of the App.

2- The username and password you entered are saved in the cookies as they are will be your tokens to check your Auth state before every request you perform inside the App, so don't try to delete your tokens from the cookies otherwise you will be logged out once you make any request inside the App and therefore you will lost all your data including your saved favorites movies [will talk about it in point (3)], as the App doesn't have any backend database that saves your works in the App. It depends ONLY on the client side [Cookies]. So deleting cookies here or clicking on the [Logout] Link in the dropdown menu in the Navbar are similar to deleting your Account forever.
2- The username and password you entered in the login form generate a unique Token that will be saved in the browser Local Storage with the username. So this unique Token & username are your tokens to check your Auth state before every request you perform inside the App, so don't try to delete your tokens from the Local Storage otherwise you will be logged out once you make any request inside the App and therefore you will lost all your data including your saved favorites movies [will talk about it in point (3)], and will lost your chosen Theme (Dark or Day) [will talk about it in point (5)]. Because the App doesn't have any backend database that saves your works in the App. It depends ONLY on the client side >> [Local Storage]. So deleting your LocalStorage here or clicking on the [Logout] Link in the dropdown menu in the Navbar are similar to deleting your Account forever.

3- You can choose any movie in the App as your favorite movie, by clicking on the heart icon at the top right of each movie poster, and this choice as a favorite movie will be saved in the Cookies also to prevent losting your favorites data if you make a reloading for the App. Also you can remove this favorite movie from your favorites list by clicking another mouse click on the heart icon again.
3- You can choose any movie in the App as your favorite movie, by clicking on the heart icon at the top right of each movie poster, and this choice as a favorite movie will be saved in the Local Storage also to prevent losting your favorites data if you make a reloading for the App. Also you can remove this favorite movie from your favorites list by clicking another mouse click on the heart icon again.

4- You can see all your favorites Movies you choosed them before by navigating to the "My Favorites Page", in the Navbar, open the dropdown menu and click on the [My Favorites] Link to go to your favorites Movies.
4- You can also see all your favorites Movies you choosed before by navigating to the "My Favorites Page", in the Navbar, open the dropdown menu and click on the [My Favorites] Link to go to your favorites Movies.

4- The App contains 4 main sliders in the Home Screen:-
5- You can choose your favorite Theme between (Dark & Day) and this choice will be saved in the Local Storage also, so your preferred Theme will not be lost after reloading the App.

6- The App contains 4 main sliders in the Home Screen:-
- The Top Slider is for the [Now Playing Movies] in the Cinema
- The Second Slider is for the [Popular Movies]
- The Third Slider is for the [Top Rated Movies]
- The Fourth is for the [Recent Rated Movies]

5- If you click on any movie, a movie modal will be opened that contains all this movie details:- [Title, Release Date, Genres, Overview, Cast, Crew, Video Trailer]
7- If you click on any movie, a movie modal will be opened that contains all this movie details:- [Title, Release Date, Genres, Overview, Cast, Crew, Video Trailer]

6- You have the ability to search for any movie you need in a large database contains millions of movies, by just typing its name letters in the search input at the top of the screen and you will get the results that match your needs.
7- You have the ability to search for any movie you need in a large database contains millions of movies, by just typing its name letters in the search input at the top of the screen and you will get the results that match your needs.

7- The App depends for its database on the TMDB Website API's, TMDB is the largest Database Website for Movies and TV Shows in the World, you can check all the API's and the URLs that this App depends on them in the (config.js) file inside the (src) folder.
8- The App depends for its database on the TMDB Website API's, TMDB is the largest Database Website for Movies and TV Shows in the World, you can check all the API's and the URLs that this App depends on them in the (config.js) file inside the (src) folder.

8- Finally, you can take this App as a reference and strong practical & revision to understand the working logic of `redux`, `react-redux` & middlware like `redux-thunk` and how they interact with a react App.
9- Finally, you can take this App as a reference and strong practical & revision to understand the working logic of `redux`, `react-redux` & middlware like `redux-thunk` and how they interact with a react App.
## License

Licensed under the [MIT License](LICENSE)
5 changes: 0 additions & 5 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 0 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@
"@testing-library/user-event": "^12.8.3",
"antd": "^4.16.13",
"axios": "^0.23.0",
"js-cookie": "^3.0.1",
"react": "^17.0.2",
"react-bootstrap": "^1.6.4",
"react-dom": "^17.0.2",
Expand Down
5 changes: 2 additions & 3 deletions src/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ import React, { useEffect } from "react";
import { BrowserRouter as Router } from "react-router-dom";
import { connect } from 'react-redux';
import { ThemeProvider } from "styled-components";
import Cookies from 'js-cookie';
import { ProvideAuth } from 'hooks';
import { switchTheme, setFavorites} from "actions";
import { Layout } from "layout";
Expand All @@ -18,15 +17,15 @@ const App = ({

useEffect(() => {

let storedTheme = Cookies.get("theme");
let storedTheme = localStorage.getItem("theme");

if(storedTheme) setTheme(storedTheme);

}, []); // eslint-disable-line

useEffect(() => {

let storedFavorites = Cookies.get("favorites");
let storedFavorites = localStorage.getItem("favorites");

if(storedFavorites) setFavoritesAction(JSON.parse(storedFavorites));

Expand Down
1 change: 1 addition & 0 deletions src/components/footer/Footer.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ const Footer = () => {
<li className="mr-3"><a href="https://codepen.io/Mohamed-ElHawary" target="_blank"><AiFillCodepenCircle size={30} /></a></li> {/* eslint-disable-line */}
<li className="mr-3"><a href="https://www.behance.net/mohamed-elhawary14" target="_blank"><AiFillBehanceCircle size={30} /></a></li> {/* eslint-disable-line */}
</ul>
<span className="fade-animation"><a href="https://github.com/Mohamed-Elhawary/cinema-universe/releases/tag/v1.0" target="_blank">Version 1.1</a></span> {/* eslint-disable-line */}
</div>
</CustomizedFooter>
);
Expand Down
5 changes: 2 additions & 3 deletions src/components/navbar/Navbar.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import { connect } from 'react-redux';
import { Dropdown, Nav, NavDropdown, Container } from 'react-bootstrap';
import { BsFillMoonFill, BsFillSunFill } from "react-icons/bs";
import { ImCross } from "react-icons/im";
import Cookies from 'js-cookie';
import { checkAuth } from "utils";
import { useAuth } from 'hooks';
import {
Expand Down Expand Up @@ -37,13 +36,13 @@ const Navbar = ({

if(theme === "dark") {

Cookies.set("theme", "light");
localStorage.setItem("theme", "light");

setTheme("light");

} else {

Cookies.set("theme", "dark");
localStorage.setItem("theme", "dark");

setTheme("dark");

Expand Down
11 changes: 5 additions & 6 deletions src/hooks/useAuth.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,7 @@ import
createContext
} from "react";
import { useDispatch } from "react-redux";
import Cookies from 'js-cookie';
import { getCookies, removeCookies, checkAuth } from "utils";
import { getTokens, removeTokensAndData, checkAuth } from "utils";
import { setFavorites } from "actions";

const authContext = createContext();
Expand Down Expand Up @@ -54,7 +53,7 @@ function useProvideAuth() {

const logout = (callback) => {

removeCookies();
removeTokensAndData();

setUser(null);

Expand All @@ -68,15 +67,15 @@ function useProvideAuth() {

setShowMainLoader(true);

const cookies = getCookies();
const tokens = getTokens();

setTimeout(() => {

if (checkAuth()) setUser(cookies['userName']);
if (checkAuth()) setUser(tokens['userName']);

else {

removeCookies();
removeTokensAndData();

setUser(null);

Expand Down
1 change: 0 additions & 1 deletion src/index.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter } from 'react-router-dom';
import { Provider } from 'react-redux';
import store from './store';
import App from './App';
Expand Down
44 changes: 15 additions & 29 deletions src/styles/GlobalStyles.js
Original file line number Diff line number Diff line change
Expand Up @@ -59,34 +59,6 @@ export const GlobalStyles = createGlobalStyle`
};
.error-404 {
font-size: 50px;
animation: fade 2s linear infinite;
@-webkit-keyframes fade {
0% {
opacity: .8
}
50% {
opacity: .6
}
100% {
opacity: 1
}
}
@keyframes fade {
0% {
opacity: .8
}
50% {
opacity: .6
}
100% {
opacity: 1;
}
}
}
};
.cross-icon {
Expand All @@ -99,7 +71,21 @@ export const GlobalStyles = createGlobalStyle`
&.show {
display: initial;
}
}
};
.fade-animation {
animation: fade 2s linear infinite;
@keyframes fade {
0% {
opacity: 1;
};
50% {
opacity: .4;
};
100% {
opacity: 1;
};
}
};
::-webkit-scrollbar {
width: 5px;
}
Expand Down
20 changes: 9 additions & 11 deletions src/utils/helpers.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
import Cookies from 'js-cookie';

export const getCookies = () => {
export const getTokens = () => {

let userName = localStorage.getItem("userName") || null;

Expand All @@ -10,21 +8,21 @@ export const getCookies = () => {

}

export const removeCookies = () => {
export const removeTokensAndData = () => {

localStorage.removeItem("userName");

localStorage.removeItem("token");

Cookies.remove("favorites");
localStorage.removeItem("favorites");

}

export const checkAuth = () => {

let cookies = getCookies();
let tokens = getTokens();

return cookies['userName'] && cookies['token'];
return tokens['userName'] && tokens['token'];

}

Expand All @@ -41,20 +39,20 @@ export const addOrRemoveMovieFromFavorites = (e, movie, favorites, callback) =>

if(checkAuth()) {

let storedFavorites = Cookies.get("favorites");
let storedFavorites = localStorage.getItem("favorites");

if(checkFavorite(favorites, movie.id)) {

callback("isFav");

if(storedFavorites) Cookies.set("favorites", JSON.stringify(JSON.parse(storedFavorites).filter(fav => fav.id !== movie.id)));
if(storedFavorites) localStorage.setItem("favorites", JSON.stringify(JSON.parse(storedFavorites).filter(fav => fav.id !== movie.id)));

} else {

callback("isNotFav");

if(storedFavorites) Cookies.set("favorites", JSON.stringify(JSON.parse(storedFavorites).concat({...movie})));
else Cookies.set("favorites", JSON.stringify([movie]));
if(storedFavorites) localStorage.setItem("favorites", JSON.stringify(JSON.parse(storedFavorites).concat({...movie})));
else localStorage.setItem("favorites", JSON.stringify([movie]));

}

Expand Down
8 changes: 4 additions & 4 deletions src/utils/index.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import axios from "./axios-instance";
import {
getCookies,
removeCookies,
getTokens,
removeTokensAndData,
checkAuth,
checkFavorite,
getCurrentDate,
Expand All @@ -12,8 +12,8 @@ import LazyLoadComponent from "./LazyLoadComponent";

export {
axios,
getCookies,
removeCookies,
getTokens,
removeTokensAndData,
checkAuth,
checkFavorite,
getCurrentDate,
Expand Down
2 changes: 1 addition & 1 deletion src/views/home/Home.js
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ const Home = ({
);

if(searchMode) UI = <Search />;
else if(fetchingLoaderState) UI = <div className="view"><SpinnerLoader large spinnerColor={theme === "light" ? "dark" : "light"} style={{top: "50%", position: "absolute"}} /></div>;
else if(fetchingLoaderState) UI = <div className="view"><SpinnerLoader large spinnerColor={theme === "light" ? "dark" : "light"} style={{top: "50%", left: "45%", position: "absolute"}} /></div>;
else UI = home;

return UI;
Expand Down
2 changes: 1 addition & 1 deletion src/views/notfound/NotFound.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ const NotFound = ({ searchMode }) => {
searchMode ? <Search /> : (
<div className="view">
<h2 className="center-text text-center error-text">
<span className="error-404 d-block">404</span>
<span className="error-404 d-block fade-animation">404</span>
Page Not Found...
</h2>
</div>
Expand Down
5 changes: 3 additions & 2 deletions src/views/search/Search.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ const Search = ({
getSearchMoviesData(searchText, pageNumber);

}

console.log(moviesData)
useEffect(() => {

if(Object.keys(moviesData).length === 0) {
Expand All @@ -33,6 +33,7 @@ const Search = ({
} else {

setFetchingLoaderState(false);

}

}, [moviesData]); // eslint-disable-line
Expand Down Expand Up @@ -71,7 +72,7 @@ const Search = ({
</div>
);

if(fetchingLoaderState) UI = <div className="view"><SpinnerLoader large spinnerColor={theme === "light" ? "dark" : "light"} style={{top: "50%", position: "absolute"}} /></div>;
if(fetchingLoaderState) UI = <div className="view"><SpinnerLoader large spinnerColor={theme === "light" ? "dark" : "light"} style={{top: "50%", left: "45%", position: "absolute"}} /></div>;
else if(moviesData?.results?.length > 0) UI = search;
else UI = <div className="view"><h2 className="center-text text-center">No Movies Found...</h2></div>;

Expand Down

0 comments on commit 74704c4

Please sign in to comment.