add logout service and adjust axios client

This commit is contained in:
NCanggoro 2023-09-27 21:54:58 +07:00
parent 5e13d85ff8
commit 19f7f6f07b
11 changed files with 85 additions and 21 deletions

View File

@ -0,0 +1,5 @@
import { LOGOUT } from "../constants/actions";
export const logout = () => ({
type: LOGOUT
});

1
src/actions/index.ts Normal file
View File

@ -0,0 +1 @@
export * from "./LogoutAction";

View File

@ -1,8 +1,10 @@
import React from "preact/compat"; import React, { TargetedEvent } from "preact/compat";
import { useState } from "preact/hooks"; import { useState } from "preact/hooks";
import './style.css'; import { useSelector, useDispatch } from "react-redux";
import { useSelector } from "react-redux";
import { UserRootState } from "../../store/type"; import { UserRootState } from "../../store/type";
import { logout } from '../../actions';
import './style.css';
import { logoutService } from "../../services";
function Header() { function Header() {
@ -12,6 +14,7 @@ function Header() {
profileMenu: false profileMenu: false
}) })
const dispatch = useDispatch();
const user = useSelector((state: UserRootState) => state.auth) const user = useSelector((state: UserRootState) => state.auth)
const onInput = (e: React.ChangeEvent<HTMLInputElement>): void => { const onInput = (e: React.ChangeEvent<HTMLInputElement>): void => {
@ -19,6 +22,16 @@ function Header() {
setSearchVal(val.value) setSearchVal(val.value)
} }
const handleLogout = async (): Promise<void> => {
try {
await logoutService()
dispatch(logout())
location.reload()
} catch (error) {
alert(error)
}
}
const onSearchSubmit = (e: React.TargetedEvent<HTMLFormElement>): void => { const onSearchSubmit = (e: React.TargetedEvent<HTMLFormElement>): void => {
e.preventDefault(); e.preventDefault();
} }
@ -52,7 +65,7 @@ function Header() {
<a href={'#'}><div className={'p-2'}>Profile</div></a> <a href={'#'}><div className={'p-2'}>Profile</div></a>
<a href={'#'}><div className={'p-2'}>Feed</div></a> <a href={'#'}><div className={'p-2'}>Feed</div></a>
<a href={'#'}><div className={'p-2'}>Add location</div></a> <a href={'#'}><div className={'p-2'}>Add location</div></a>
<a href={'#'}><div className={'p-2'}>Logout</div></a> <a href={'#'} onClick={handleLogout}><div className={'p-2'}>Logout</div></a>
{/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */} {/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */}
{/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */} {/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */}
</div> </div>
@ -89,7 +102,7 @@ function Header() {
<a href={'#'}><div className={'p-1'}>Profile</div></a> <a href={'#'}><div className={'p-1'}>Profile</div></a>
<a href={'#'}><div className={'p-1'}>Feed</div></a> <a href={'#'}><div className={'p-1'}>Feed</div></a>
<a href={'#'}><div className={'p-1'}>Add location</div></a> <a href={'#'}><div className={'p-1'}>Add location</div></a>
<a href={'#'}><div className={'p-1'}>Logout</div></a> <a href={'#'} onClick={handleLogout}><div className={'p-1'}>Logout</div></a>
{/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */} {/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */}
{/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */} {/* <div className={'p-2'}><a href={'#'}>Halo</a></div> */}
</div> </div>

View File

@ -2,7 +2,7 @@ const BASE_URL = "http://localhost:8888"
const SIGNUP_URI = `${BASE_URL}/user/signup` const SIGNUP_URI = `${BASE_URL}/user/signup`
const LOGIN_URI = `${BASE_URL}/user/login` const LOGIN_URI = `${BASE_URL}/user/login`
const LOGOUT_URI = `${BASE_URL}/user/logout`
const GET_LIST_LOCATIONS_URI = `${BASE_URL}/locations`; const GET_LIST_LOCATIONS_URI = `${BASE_URL}/locations`;
const GET_LIST_TOP_LOCATIONS = `${BASE_URL}/locations/top-ratings` const GET_LIST_TOP_LOCATIONS = `${BASE_URL}/locations/top-ratings`
@ -12,14 +12,18 @@ const GET_LOCATION_TAGS_URI = `${BASE_URL}/location/tags`
const GET_IMAGES_BY_LOCATION_URI = `${BASE_URL}/images/location` const GET_IMAGES_BY_LOCATION_URI = `${BASE_URL}/images/location`
const POST_REVIEW_LOCATION_URI = `${BASE_URL}/review/location`
export { export {
BASE_URL, BASE_URL,
SIGNUP_URI, SIGNUP_URI,
LOGIN_URI, LOGIN_URI,
LOGOUT_URI,
GET_LIST_RECENT_LOCATIONS_RATING_URI, GET_LIST_RECENT_LOCATIONS_RATING_URI,
GET_LIST_TOP_LOCATIONS, GET_LIST_TOP_LOCATIONS,
GET_LIST_LOCATIONS_URI, GET_LIST_LOCATIONS_URI,
GET_LOCATION_URI, GET_LOCATION_URI,
GET_LOCATION_TAGS_URI, GET_LOCATION_TAGS_URI,
GET_IMAGES_BY_LOCATION_URI, GET_IMAGES_BY_LOCATION_URI,
POST_REVIEW_LOCATION_URI
} }

2
src/constants/default.ts Normal file
View File

@ -0,0 +1,2 @@
export const DEFAULT_AVATAR_IMG = 'https://cdn.discordapp.com/attachments/743422487882104837/1153985664849805392/421-4212617_person-placeholder-image-transparent-hd-png-download.png';

View File

@ -1,12 +1,13 @@
import { ChangeEvent, TargetedEvent, useState } from "preact/compat"; import { ChangeEvent, TargetedEvent, useState } from "preact/compat";
import { createAccountService, loginService } from "../../services"; import { createAccountService, loginService } from "../../services";
import { useNavigate } from "react-router-dom"; import { useLocation, useNavigate } from "react-router-dom";
import { useDispatch } from "react-redux"; import { useDispatch } from "react-redux";
import { authAdded } from "../../features/auth/authSlice/authSlice"; import { authAdded } from "../../features/auth/authSlice/authSlice";
import './index.css'; import './index.css';
function Login() { function Login() {
const dispatch = useDispatch(); const dispatch = useDispatch();
const { state } = useLocation()
const [form, setFrom] = useState({ const [form, setFrom] = useState({
username: '', username: '',
password: '' password: ''
@ -27,9 +28,16 @@ function Login() {
setErrorMsg(res.error.response.data.errors) setErrorMsg(res.error.response.data.errors)
return return
} }
dispatch(authAdded(res.data)) dispatch(authAdded(res.data))
// localStorage.setItem("user", JSON.stringify(res.data))
if (state) {
navigation(state.from)
return
}
navigation("/") navigation("/")
} catch (err) { } catch (err) {
console.log(err) console.log(err)
} }
@ -47,7 +55,15 @@ function Login() {
setErrorMsg(res.error.response.data.errors) setErrorMsg(res.error.response.data.errors)
return; return;
} }
console.log(res.data)
dispatch(authAdded(res.data))
if (state) {
navigation(state.from)
return
}
navigation("/")
} catch (err) { } catch (err) {
alert(err) alert(err)
} }

View File

@ -14,9 +14,8 @@ interface IAuthentication {
async function createAccountService({ username, password }: IAuthentication) { async function createAccountService({ username, password }: IAuthentication) {
const newState = { ...initialState }; const newState = { ...initialState };
const url = `${SIGNUP_URI}`
try { try {
const response = await client({ method: 'POST', url: url, data: { username, password } }) const response = await client({ method: 'POST', url: SIGNUP_URI, data: { username, password } })
newState.data = response.data newState.data = response.data
newState.error = null newState.error = null
return newState return newState
@ -28,9 +27,8 @@ async function createAccountService({ username, password }: IAuthentication) {
async function loginService({ username, password }: IAuthentication) { async function loginService({ username, password }: IAuthentication) {
const newState = { ...initialState }; const newState = { ...initialState };
const url = `${LOGIN_URI}`
try { try {
const response = await client({ method: 'POST', url: url, data: { username, password } }) const response = await client({ method: 'POST', url: LOGIN_URI, data: { username, password }, withCredentials: true })
newState.data = response.data newState.data = response.data
newState.error = null newState.error = null
return newState return newState
@ -41,7 +39,21 @@ async function loginService({ username, password }: IAuthentication) {
} }
async function logoutService() {
const newState = { ...initialState };
try {
const response = await client({ method: 'POST', url: LOGIN_URI})
newState.data = response.data
newState.error = null
return newState
} catch (error) {
newState.error = error
return newState
}
}
export { export {
loginService, loginService,
createAccountService createAccountService,
logoutService
}; };

View File

@ -6,7 +6,8 @@ export const client = (props: AxiosRequestConfig): AxiosPromise => axios({
baseURL: `${BASE_URL}`, baseURL: `${BASE_URL}`,
url: props.url, url: props.url,
headers: props.headers, headers: props.headers,
data: props.data data: props.data,
...props
}) })
// export const authClient = (props: AxiosRequestConfig) => axios({ // export const authClient = (props: AxiosRequestConfig) => axios({

View File

@ -5,13 +5,14 @@ import {
getLocationService, getLocationService,
getLocationTagsService, getLocationTagsService,
} from "./locations"; } from "./locations";
import { getImagesByLocationService } from "./images" import { getImagesByLocationService } from "./images"
import { createAccountService, loginService } from "./auth"; import { createAccountService, loginService, logoutService } from "./auth";
import { postReviewLocation } from "./review";
export { export {
createAccountService, createAccountService,
loginService, loginService,
logoutService,
getListLocationsService, getListLocationsService,
getListRecentLocationsRatingsService, getListRecentLocationsRatingsService,
@ -19,4 +20,6 @@ export {
getLocationService, getLocationService,
getLocationTagsService, getLocationTagsService,
getImagesByLocationService, getImagesByLocationService,
postReviewLocation
} }

View File

@ -0,0 +1,5 @@
import { AxiosError } from "axios";
export function handleAxiosError(error: AxiosError) {
return error.response?.data
}

View File

@ -1,5 +1,7 @@
import useAutosizeTextArea from "./useAutosizeTextArea"; import useAutosizeTextArea from "./useAutosizeTextArea";
import { handleAxiosError } from "./common";
export { export {
useAutosizeTextArea useAutosizeTextArea,
handleAxiosError
} }