Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Contribute to GitLab
Sign in
Toggle navigation
P
products_lesson_front
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Pavel Mishakov
products_lesson_front
Commits
07b61617
Commit
07b61617
authored
Mar 25, 2023
by
Pavel Mishakov
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
add token check and Private route
parent
db6fb5cb
Hide whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
65 additions
and
53 deletions
+65
-53
App.tsx
src/App.tsx
+15
-29
instance.ts
src/api/instance.ts
+10
-1
Header.tsx
src/components/Header/Header.tsx
+0
-12
ILayoutProps.ts
src/components/Layout/ILayoutProps.ts
+0
-5
Layout.tsx
src/components/Layout/Layout.tsx
+3
-3
Login.tsx
src/containers/Login/Login.tsx
+10
-2
users.slice.ts
src/store/users/users.slice.ts
+3
-1
PrivateRoute.tsx
src/utils/PrivateRoute.tsx
+24
-0
No files found.
src/App.tsx
View file @
07b61617
...
...
@@ -2,38 +2,24 @@ import Layout from "./components/Layout/Layout";
import
{
Routes
,
Route
}
from
"react-router-dom"
;
import
ProductFormPage
from
"./containers/ProductFormPage/ProductFormPage"
;
import
ProductsPage
from
"./containers/ProductsPage/ProductsPage"
;
import
{
AppDispatch
,
AppState
}
from
"./store/store"
;
import
{
shallowEqual
,
useDispatch
,
useSelector
}
from
"react-redux"
;
import
{
useEffect
}
from
"react"
;
import
{
checkToken
}
from
"./store/users/users.slice"
;
import
Login
from
"./containers/Login/Login"
;
import
Register
from
"./containers/Register/Register"
;
import
PrivateRoute
from
"./utils/PrivateRoute"
;
const
App
=
()
=>
{
const
dispatch
:
AppDispatch
=
useDispatch
()
const
{
isAuth
}
=
useSelector
((
state
:
AppState
)
=>
state
.
users
,
shallowEqual
)
useEffect
(()
=>
{
dispatch
(
checkToken
())
},
[])
return
(
<
Layout
>
{
isAuth
?
<
Routes
>
<
Route
path=
{
'/'
}
element=
{
<
h1
>
HOME
</
h1
>
}
/>
<
Route
path=
{
'/products'
}
element=
{
<
ProductsPage
/>
}
/>
<
Route
path=
{
'/add-product'
}
element=
{
<
ProductFormPage
/>
}
/>
</
Routes
>
:
<
Routes
>
<
Route
path=
{
'/'
}
element=
{
<
Login
/>
}
/>
<
Route
path=
{
'/register'
}
element=
{
<
Register
/>
}
/>
</
Routes
>
}
</
Layout
>
)
}
<
Routes
>
<
Route
element=
{
<
PrivateRoute
/>
}
>
<
Route
element=
{
<
Layout
/>
}
>
<
Route
path=
{
"/"
}
element=
{
<
h1
>
HOME
</
h1
>
}
/>
<
Route
path=
{
"/products"
}
element=
{
<
ProductsPage
/>
}
/>
<
Route
path=
{
"/add-product"
}
element=
{
<
ProductFormPage
/>
}
/>
</
Route
>
</
Route
>
<
Route
path=
{
"/login"
}
element=
{
<
Login
/>
}
/>
<
Route
path=
{
"/register"
}
element=
{
<
Register
/>
}
/>
</
Routes
>
);
};
export
default
App
export
default
App
;
src/api/instance.ts
View file @
07b61617
import
axios
from
"axios"
;
import
axios
,
{
InternalAxiosRequestConfig
}
from
"axios"
;
export
const
instance
=
axios
.
create
({
baseURL
:
import
.
meta
.
env
.
VITE_BASE_URL
})
instance
.
interceptors
.
request
.
use
((
req
:
InternalAxiosRequestConfig
)
=>
{
const
token
=
localStorage
.
getItem
(
'token'
)
if
(
token
)
{
req
.
headers
.
Authorization
=
token
}
return
req
})
\ No newline at end of file
src/components/Header/Header.tsx
View file @
07b61617
...
...
@@ -5,11 +5,9 @@ import { AppState } from "../../store/store";
import
styles
from
"./Header.module.css"
;
const
Header
:
FunctionComponent
=
():
ReactElement
=>
{
const
{
isAuth
}
=
useSelector
((
state
:
AppState
)
=>
state
.
users
,
shallowEqual
)
return
(
<
header
className=
{
styles
.
Header
}
>
{
isAuth
?
(
<>
<
NavLink
className=
{
styles
.
Header__link
}
to=
{
"/add-product"
}
>
Add product
...
...
@@ -18,16 +16,6 @@ const Header: FunctionComponent = (): ReactElement => {
Products
</
NavLink
>
</>
)
:
(
<>
<
NavLink
className=
{
styles
.
Header__link
}
to=
{
"/register"
}
>
Sign up
</
NavLink
>
<
NavLink
className=
{
styles
.
Header__link
}
to=
{
"/"
}
>
Login
</
NavLink
>
</>
)
}
</
header
>
);
};
...
...
src/components/Layout/ILayoutProps.ts
deleted
100644 → 0
View file @
db6fb5cb
import
{
ReactNode
}
from
"react"
;
export
default
interface
ILayoutProps
{
children
:
ReactNode
}
\ No newline at end of file
src/components/Layout/Layout.tsx
View file @
07b61617
import
React
,
{
FunctionComponent
,
ReactElement
}
from
"react"
;
import
{
Outlet
}
from
"react-router-dom"
;
import
Header
from
"../Header/Header"
;
import
ILayoutProps
from
"./ILayoutProps"
;
import
styles
from
'./Layout.module.css'
const
Layout
:
FunctionComponent
<
ILayoutProps
>
=
(
props
):
ReactElement
=>
{
const
Layout
:
FunctionComponent
=
(
):
ReactElement
=>
{
return
(
<
div
className=
{
styles
.
Layout
}
>
<
Header
/>
<
main
>
{
props
.
children
}
<
Outlet
/>
</
main
>
</
div
>
)
...
...
src/containers/Login/Login.tsx
View file @
07b61617
import
React
,
{
useState
}
from
'react'
import
React
,
{
use
Effect
,
use
State
}
from
'react'
import
IUserDto
from
'../../interfaces/IUserCreateDto'
import
styles
from
'./Login.module.css'
import
{
Link
}
from
'react-router-dom'
import
{
Link
,
useLocation
,
useNavigate
}
from
'react-router-dom'
import
{
shallowEqual
,
useDispatch
,
useSelector
}
from
'react-redux'
import
{
AppDispatch
,
AppState
}
from
'../../store/store'
import
{
login
}
from
'../../store/users/users.slice'
...
...
@@ -10,6 +10,9 @@ import {login} from '../../store/users/users.slice'
const
Login
:
React
.
FunctionComponent
=
():
React
.
ReactElement
=>
{
const
{
messageUser
}
=
useSelector
((
state
:
AppState
)
=>
state
.
users
,
shallowEqual
)
const
dispatch
:
AppDispatch
=
useDispatch
()
const
navigate
=
useNavigate
()
const
location
=
useLocation
()
const
{
isAuth
}
=
useSelector
((
state
:
AppState
)
=>
state
.
users
,
shallowEqual
)
const
[
values
,
setValues
]
=
useState
<
IUserDto
>
({
username
:
''
,
password
:
''
...
...
@@ -23,6 +26,11 @@ const Login: React.FunctionComponent = (): React.ReactElement => {
e
.
preventDefault
()
dispatch
(
login
(
values
))
}
useEffect
(()
=>
{
if
(
isAuth
)
{
navigate
(
location
.
state
?.
from
?
location
.
state
.
from
:
'/'
)
}
},
[
isAuth
])
return
(
<>
<
div
>
...
...
src/store/users/users.slice.ts
View file @
07b61617
...
...
@@ -34,7 +34,7 @@ export const usersSlice = createSlice({
name
:
namespace
,
initialState
:
{
user
:
{}
as
IUser
,
isAuth
:
false
,
isAuth
:
!!
localStorage
.
getItem
(
'token'
)
||
false
,
loadingUser
:
false
,
messageUser
:
''
}
as
IUsersState
,
...
...
@@ -86,6 +86,8 @@ export const usersSlice = createSlice({
state
.
messageUser
=
action
.
payload
.
message
if
(
user
)
{
state
.
isAuth
=
true
}
else
{
state
.
isAuth
=
false
}
})
}
...
...
src/utils/PrivateRoute.tsx
0 → 100644
View file @
07b61617
import
React
,
{
useEffect
}
from
'react'
import
{
shallowEqual
,
useDispatch
,
useSelector
}
from
'react-redux'
import
{
Navigate
,
Outlet
,
useLocation
}
from
'react-router-dom'
import
{
AppDispatch
,
AppState
}
from
'../store/store'
import
{
checkToken
}
from
'../store/users/users.slice'
const
PrivateRoute
:
React
.
FunctionComponent
=
():
React
.
ReactElement
=>
{
const
{
isAuth
}
=
useSelector
((
state
:
AppState
)
=>
state
.
users
,
shallowEqual
)
const
location
=
useLocation
()
const
dispatch
:
AppDispatch
=
useDispatch
()
useEffect
(()
=>
{
dispatch
(
checkToken
())
},
[
isAuth
])
return
(
isAuth
?
<
Outlet
/>
:
<
Navigate
to=
'/login'
replace
state=
{
{
from
:
location
}
}
/>
)
}
export
default
PrivateRoute
\ No newline at end of file
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment