By Hemanta Sundaray on 2021-10-30
Copy and paste the following code snippets in their respective files.
import React from "react";
import ReactDOM from "react-dom";
import "./index.css";
import App from "./App";
import store from "./store";
import { BrowserRouter as Router } from "react-router-dom";
import { Provider } from "react-redux";
ReactDOM.render(
<Provider store={store}>
<Router>
<App />
</Router>
</Provider>,
document.getElementById("root")
);
import React, { useEffect } from "react";
import Home from "./components/Home";
import Header from "./components/Header";
import Google from "./components/Google";
import { Switch, Route } from "react-router-dom";
import { useDispatch } from "react-redux";
import { googleLogin } from "./components/stateSlices/googleloginSlice";
const App = () => {
const dispatch = useDispatch();
useEffect(() => {
dispatch(googleLogin());
}, [dispatch]);
return (
<>
<Header />
<main>
<Switch>
<Route path="/google">
<Google />
</Route>
<Route path="/">
<Home />
</Route>
</Switch>
</main>
</>
);
};
export default App;
LINE:12-14 - When the application starts, we make a GET request to the /api/currentUser route and try to find out whether the user is logged in or not.
* {
padding: 0;
margin: 0;
box-sizing: border-box;
}
html {
font-size: 62.5%;
font-family: sans-serif;
}
header {
width: 100%;
height: 6rem;
background-color: black;
}
nav {
width: 100%;
height: 100%;
}
nav ul {
width: 100%;
height: 100%;
list-style: none;
display: flex;
justify-content: flex-start;
align-items: center;
padding: 0 1rem;
}
nav ul li:not(:last-child) {
margin-right: 1rem;
}
nav a {
font-size: 1.5rem;
text-decoration: none;
}
nav a:link,
a:visited {
color: gray;
}
nav a:hover {
color: white;
}
nav a:active {
color: limegreen;
}
main {
margin: 2rem;
}
.active {
font-weight: 900;
}
.sign-out {
border: 0.1rem solid gray;
border-radius: 0.3rem;
padding: 0.2rem;
}
import React from "react";
import { useSelector } from "react-redux";
const Home = () => {
const { googleUser } = useSelector((state) => state.google);
console.log(googleUser);
return (
<>
<h1>Home</h1>
<h3>Hi {googleUser ? googleUser.givenName : "Stranger"}</h3>
</>
);
};
export default Home;
import React from "react";
import { NavLink } from "react-router-dom";
import { useDispatch, useSelector } from "react-redux";
const Header = () => {
const { googleUser } = useSelector((state) => state.google);
const dispatch = useDispatch();
return (
<header>
<nav>
<ul>
<li>
<NavLink to="/" exact activeClassName="active">
Home
</NavLink>
</li>
<li>
{googleUser ? (
<a href="/api/logout" className="sign-out">
Sign out
</a>
) : (
<ul>
<li>
<NavLink to="/google" activeClassName="active">
Google
</NavLink>
</li>
</ul>
)}
</li>
</ul>
</nav>
</header>
);
};
export default Header;
import React from "react";
const Google = () => {
return (
<a href="/auth/google" className="google-link">
<img src="google_signin.png" />
</a>
);
};
export default Google;
The Sign in with Google button can be downloaded at the link here.
import { createSlice, createAsyncThunk } from "@reduxjs/toolkit";
import axios from "axios";
const initialState = {
status: "idle",
googleUser: null,
error: null,
};
export const googleLogin = createAsyncThunk(
"google/googleLogin",
async (_, { rejectWithValue }) => {
try {
const { data } = await axios.get("/api/currentUser");
return data;
} catch (err) {
return rejectWithValue(err.response.data);
}
}
);
export const googleloginSlice = createSlice({
name: "google",
initialState,
reducers: {},
extraReducers: {
[googleLogin.pending]: (state, action) => {
state.status = "loading";
},
[googleLogin.fulfilled]: (state, action) => {
state.status = "succeeded";
state.googleUser = action.payload;
},
[googleLogin.rejected]: (state, action) => {
state.status = "failed";
state.error = action.payload.message;
},
},
});
export default googleloginSlice.reducer;