apply suggestions
continuous-integration/drone/push Build is passing Details

pull/107/head
maxime 1 year ago
parent defd53c9bc
commit 73dfa0077d

@ -2,7 +2,7 @@ import { BrowserRouter, Outlet, Route, Routes } from "react-router-dom"
import { Header } from "./pages/template/Header.tsx" import { Header } from "./pages/template/Header.tsx"
import "./style/app.css" import "./style/app.css"
import { lazy } from "react" import { lazy, ReactNode, Suspense } from "react"
import { BASE } from "./Constants.ts" import { BASE } from "./Constants.ts"
const HomePage = lazy(() => import("./pages/HomePage.tsx")) const HomePage = lazy(() => import("./pages/HomePage.tsx"))
@ -15,41 +15,58 @@ const NewTacticPage = lazy(() => import("./pages/NewTacticPage.tsx"))
const Editor = lazy(() => import("./pages/Editor.tsx")) const Editor = lazy(() => import("./pages/Editor.tsx"))
export default function App() { export default function App() {
function suspense(node: ReactNode) {
return (
<Suspense fallback={<p>Loading, please wait...suspense(</p>}>
{node}
</Suspense>
)
}
return ( return (
<div id="app"> <div id="app">
<BrowserRouter basename={BASE}> <BrowserRouter basename={BASE}>
<Outlet /> <Outlet />
<Routes> <Routes>
<Route path={"/login"} element={<LoginPage />} /> <Route path={"/login"} element={suspense(<LoginPage />)} />
<Route path={"/register"} element={<RegisterPage />} /> <Route
path={"/register"}
element={suspense(<RegisterPage />)}
/>
<Route path={"/"} element={<AppLayout />}> <Route path={"/"} element={suspense(<AppLayout />)}>
<Route path={"/"} element={<HomePage />} /> <Route path={"/"} element={suspense(<HomePage />)} />
<Route path={"/home"} element={<HomePage />} /> <Route
path={"/home"}
element={suspense(<HomePage />)}
/>
<Route <Route
path={"/team/new"} path={"/team/new"}
element={<CreateTeamPage />} element={suspense(<CreateTeamPage />)}
/> />
<Route <Route
path={"/team/:teamId"} path={"/team/:teamId"}
element={<TeamPanelPage />} element={suspense(<TeamPanelPage />)}
/> />
<Route <Route
path={"/tactic/new"} path={"/tactic/new"}
element={<NewTacticPage />} element={suspense(<NewTacticPage />)}
/> />
<Route <Route
path={"/tactic/:tacticId/edit"} path={"/tactic/:tacticId/edit"}
element={<Editor guestMode={false} />} element={suspense(<Editor guestMode={false} />)}
/> />
<Route <Route
path={"/tactic/edit-guest"} path={"/tactic/edit-guest"}
element={<Editor guestMode={true} />} element={suspense(<Editor guestMode={true} />)}
/> />
<Route path={"*"} element={<NotFoundPage />} /> <Route
path={"*"}
element={suspense(<NotFoundPage />)}
/>
</Route> </Route>
</Routes> </Routes>
</BrowserRouter> </BrowserRouter>

@ -2,7 +2,7 @@ import {
CSSProperties, CSSProperties,
Dispatch, Dispatch,
RefObject, RefObject,
SetStateAction, startTransition, SetStateAction,
useCallback, useCallback,
useEffect, useEffect,
useMemo, useMemo,
@ -119,7 +119,7 @@ export default function EditorPage({ guestMode }: EditorPageProps) {
async function initialize() { async function initialize() {
const infoResponsePromise = fetchAPIGet(`tactics/${id}`) const infoResponsePromise = fetchAPIGet(`tactics/${id}`)
const contentResponsePromise = fetchAPIGet(`tactics/${id}/1`) const contentResponsePromise = fetchAPIGet(`tactics/${id}/steps/1`)
const infoResponse = await infoResponsePromise const infoResponse = await infoResponsePromise
const contentResponse = await contentResponsePromise const contentResponse = await contentResponsePromise
@ -130,7 +130,7 @@ export default function EditorPage({ guestMode }: EditorPageProps) {
} }
const { name, courtType } = await infoResponse.json() const { name, courtType } = await infoResponse.json()
const { content } = await contentResponse.json() const content = await contentResponse.text()
setTactic({ id, name, courtType, content }) setTactic({ id, name, courtType, content })
} }
@ -192,13 +192,13 @@ function Editor({ id, name, courtType, content }: EditorProps) {
return SaveStates.Guest return SaveStates.Guest
} }
const response = await fetchAPI( const response = await fetchAPI(
`tactics/${id}/1`, `tactics/${id}/steps/1`,
{ content }, { content },
"PUT", "PUT",
) )
if (response.status == 401) startTransition(() => { if (response.status == 401) {
navigate("/login") navigate("/login")
}) }
return response.ok ? SaveStates.Ok : SaveStates.Err return response.ok ? SaveStates.Ok : SaveStates.Err
}} }}
onNameChange={async (name: string) => { onNameChange={async (name: string) => {
@ -212,9 +212,9 @@ function Editor({ id, name, courtType, content }: EditorProps) {
{ name }, { name },
"PUT", "PUT",
) )
if (response.status == 401) startTransition(() => { if (response.status == 401) {
navigate("/login") navigate("/login")
}) }
return response.ok return response.ok
}} }}
/> />

@ -1,7 +1,7 @@
import "../style/home/home.css" import "../style/home/home.css"
import { getSession } from "../api/session.ts" import { getSession } from "../api/session.ts"
import { useNavigate } from "react-router-dom" import { useNavigate } from "react-router-dom"
import { startTransition, useEffect, useState } from "react" import { useEffect, useState } from "react"
import { User } from "../model/User.ts" import { User } from "../model/User.ts"
import { fetchAPIGet } from "../Fetcher.ts" import { fetchAPIGet } from "../Fetcher.ts"
@ -32,9 +32,7 @@ export default function HomePage() {
const session = getSession() const session = getSession()
if (!session.auth) { if (!session.auth) {
startTransition(() => {
navigate("/login") navigate("/login")
})
return return
} }
@ -177,9 +175,7 @@ function TableData({ allTactics }: { allTactics: Tactic[] }) {
key={tactic.id} key={tactic.id}
className="data" className="data"
onClick={() => { onClick={() => {
startTransition(() => {
navigate("/tactic/" + tactic.id + "/edit") navigate("/tactic/" + tactic.id + "/edit")
})
}}> }}>
{truncateString(tactic.name, 25)} {truncateString(tactic.name, 25)}
</td> </td>
@ -194,25 +190,25 @@ function TableData({ allTactics }: { allTactics: Tactic[] }) {
} }
} }
const data = listTactic.map((tactic, rowIndex) => ( return listTactic.map((tactic, rowIndex) => (
<tr key={rowIndex + "row"}>{tactic}</tr> <tr key={rowIndex + "row"}>{tactic}</tr>
)) ))
return data
} }
function BodyPersonalSpace({ allTactics }: { allTactics: Tactic[] }) { function BodyPersonalSpace({ allTactics }: { allTactics: Tactic[] }) {
let data
if (allTactics.length == 0) {
data = <p>Aucune tactique créée !</p>
} else {
data = <TableData allTactics={allTactics} />
}
return ( return (
<div id="body-personal-space"> <div id="body-personal-space">
{
allTactics.length == 0
? <p>Aucune tactique créée !</p>
:
<table> <table>
<tbody key="tbody">{data}</tbody> <tbody key="tbody">
<TableData allTactics={allTactics} />
</tbody>
</table> </table>
}
</div> </div>
) )
} }
@ -223,7 +219,7 @@ function Team({ teams }: { teams: Team[] }) {
<div id="teams"> <div id="teams">
<div className="titre-side-menu"> <div className="titre-side-menu">
<h2 className="title">Mes équipes</h2> <h2 className="title">Mes équipes</h2>
<button className="new" onClick={() => startTransition(() => navigate("/team/new"))}> <button className="new" onClick={() => navigate("/team/new")}>
+ +
</button> </button>
</div> </div>
@ -242,7 +238,7 @@ function Tactic({ lastTactics }: { lastTactics: Tactic[] }) {
<button <button
className="new" className="new"
id="create-tactic" id="create-tactic"
onClick={() => startTransition(() => navigate("/tactic/new"))}> onClick={() => navigate("/tactic/new")}>
+ +
</button> </button>
</div> </div>
@ -275,9 +271,7 @@ function ButtonTeam({ team }: { team: Team }) {
id={"button-team" + team.id} id={"button-team" + team.id}
className="button-side-menu data" className="button-side-menu data"
onClick={() => { onClick={() => {
startTransition(() => {
navigate("/team/" + team.id) navigate("/team/" + team.id)
})
}}> }}>
{name} {name}
</div> </div>
@ -294,9 +288,7 @@ function ButtonLastTactic({ tactic }: { tactic: Tactic }) {
id={"button" + tactic.id} id={"button" + tactic.id}
className="button-side-menu data" className="button-side-menu data"
onClick={() => { onClick={() => {
startTransition(() => {
navigate("/tactic/" + tactic.id + "/edit") navigate("/tactic/" + tactic.id + "/edit")
})
}}> }}>
{name} {name}
</div> </div>

@ -1,4 +1,4 @@
import { FormEvent, startTransition, useState } from "react" import { FormEvent, useState } from "react"
import { fetchAPI } from "../Fetcher.ts" import { fetchAPI } from "../Fetcher.ts"
import { Failure } from "../api/failure.ts" import { Failure } from "../api/failure.ts"
import { getSession, saveSession } from "../api/session.ts" import { getSession, saveSession } from "../api/session.ts"
@ -31,9 +31,7 @@ export default function LoginApp() {
auth: { token, expirationDate }, auth: { token, expirationDate },
urlTarget: undefined, urlTarget: undefined,
}) })
startTransition(() => {
navigate(session.urlTarget ?? "/") navigate(session.urlTarget ?? "/")
})
return return
} }
@ -85,7 +83,13 @@ export default function LoginApp() {
<form onSubmit={handleSubmit}> <form onSubmit={handleSubmit}>
<div className="form-group"> <div className="form-group">
<label htmlFor="email">Email :</label> <label htmlFor="email">Email :</label>
<input className="text-input" type="text" id="email" name="email" required /> <input
className="text-input"
type="text"
id="email"
name="email"
required
/>
<label htmlFor="password">Mot de passe :</label> <label htmlFor="password">Mot de passe :</label>
<input <input

@ -4,7 +4,7 @@ import "../style/new_tactic_panel.css"
import plainCourt from "../assets/court/full_court.svg" import plainCourt from "../assets/court/full_court.svg"
import halfCourt from "../assets/court/half_court.svg" import halfCourt from "../assets/court/half_court.svg"
import { CourtType } from "../model/tactic/Tactic.ts" import { CourtType } from "../model/tactic/Tactic.ts"
import { startTransition, useCallback } from "react" import { useCallback } from "react"
import { fetchAPI } from "../Fetcher.ts" import { fetchAPI } from "../Fetcher.ts"
import { getSession } from "../api/session.ts" import { getSession } from "../api/session.ts"
import { useNavigate } from "react-router-dom" import { useNavigate } from "react-router-dom"
@ -52,9 +52,7 @@ function CourtKindButton({
onClick={useCallback(async () => { onClick={useCallback(async () => {
// if user is not authenticated // if user is not authenticated
if (!getSession().auth) { if (!getSession().auth) {
startTransition(() => {
navigate(`/tactic/edit-guest`) navigate(`/tactic/edit-guest`)
})
} }
const response = await fetchAPI( const response = await fetchAPI(
@ -66,16 +64,14 @@ function CourtKindButton({
"POST", "POST",
) )
if (response.status === 401) startTransition(() => { if (response.status === 401) {
// if unauthorized // if unauthorized
navigate("/login") navigate("/login")
return return
}) }
const { id } = await response.json() const { id } = await response.json()
startTransition(() => {
navigate(`/tactic/${id}/edit`) navigate(`/tactic/${id}/edit`)
})
}, [courtType, navigate])}> }, [courtType, navigate])}>
<div className="court-kind-button-top"> <div className="court-kind-button-top">
<div className="court-kind-button-image-div"> <div className="court-kind-button-image-div">

@ -1,4 +1,4 @@
import { FormEvent, startTransition, useRef, useState } from "react" import { FormEvent, useRef, useState } from "react"
import "../style/form.css" import "../style/form.css"
import { Failure } from "../api/failure.ts" import { Failure } from "../api/failure.ts"
@ -50,9 +50,7 @@ export default function RegisterPage() {
auth: { token, expirationDate }, auth: { token, expirationDate },
urlTarget: undefined, urlTarget: undefined,
}) })
startTransition(() => {
navigate(session.urlTarget ?? "/") navigate(session.urlTarget ?? "/")
})
return return
} }
@ -135,9 +133,7 @@ export default function RegisterPage() {
/> />
<label className="consentement"> <label className="consentement">
<input type="checkbox" <input type="checkbox" name="consentement" required />
name="consentement"
required />
En cochant cette case, j'accepte que mes données En cochant cette case, j'accepte que mes données
personnelles, tel que mon adresse e-mail, soient personnelles, tel que mon adresse e-mail, soient
collectées et traitées conformément à la politique de collectées et traitées conformément à la politique de

@ -1,6 +1,6 @@
import AccountSvg from "../../assets/account.svg?react" import AccountSvg from "../../assets/account.svg?react"
import "../../style/template/header.css" import "../../style/template/header.css"
import { startTransition, useEffect, useState } from "react" import { useEffect, useState } from "react"
import { fetchAPIGet } from "../../Fetcher.ts" import { fetchAPIGet } from "../../Fetcher.ts"
import { getSession, saveSession } from "../../api/session.ts" import { getSession, saveSession } from "../../api/session.ts"
import { useLocation, useNavigate } from "react-router-dom" import { useLocation, useNavigate } from "react-router-dom"
@ -41,7 +41,7 @@ export function Header() {
<p <p
id="iqball" id="iqball"
className="clickable" className="clickable"
onClick={() => startTransition(() => navigate("/"))}> onClick={() => navigate("/")}>
IQBall IQBall
</p> </p>
</div> </div>
@ -51,9 +51,7 @@ export function Header() {
id="clickable-header-right" id="clickable-header-right"
onClick={() => { onClick={() => {
if (username) { if (username) {
startTransition(() => {
navigate("/settings") navigate("/settings")
})
return return
} }
saveSession({ saveSession({
@ -61,9 +59,7 @@ export function Header() {
urlTarget: location.pathname, urlTarget: location.pathname,
}) })
startTransition(() => {
navigate("/login") navigate("/login")
})
}}> }}>
{/* <AccountSvg id="img-account" /> */} {/* <AccountSvg id="img-account" /> */}
<AccountSvg id="img-account" /> <AccountSvg id="img-account" />

@ -18,6 +18,10 @@
align-self: center; align-self: center;
} }
#body-personal-space > p {
text-align: center;
}
#body-personal-space table { #body-personal-space table {
width: 100%; width: 100%;
border-collapse: separate; border-collapse: separate;

@ -43,7 +43,6 @@
#clickable-header-right { #clickable-header-right {
border-radius: 1cap; border-radius: 1cap;
display: flex; display: flex;
align-items: center; align-items: center;
justify-content: space-evenly; justify-content: space-evenly;

@ -1,5 +1,3 @@
.title-input { .title-input {
background: transparent; background: transparent;
border-top: none; border-top: none;

Loading…
Cancel
Save