From dde6eaa8d4ac40912243e3fba929e1d9bfe9b28d Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Sun, 3 Dec 2023 13:59:21 +0100 Subject: [PATCH 01/22] Completing team's actions, adding css and implementing account within the teams --- sql/setup-tables.sql | 2 +- src/App/Controller/TeamController.php | 11 +++++++++++ src/Core/Gateway/TeamGateway.php | 2 +- src/Core/Model/TeamModel.php | 3 +++ 4 files changed, 16 insertions(+), 2 deletions(-) diff --git a/sql/setup-tables.sql b/sql/setup-tables.sql index eb74877..7c012eb 100644 --- a/sql/setup-tables.sql +++ b/sql/setup-tables.sql @@ -46,5 +46,5 @@ CREATE TABLE Member id_user integer, role text CHECK (role IN ('Coach', 'Player')), FOREIGN KEY (id_team) REFERENCES Team (id), - FOREIGN KEY (id_user) REFERENCES User (id) + FOREIGN KEY (id_user) REFERENCES Account (id) ); diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index b2c0ea9..e90ae67 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -4,6 +4,7 @@ namespace IQBall\App\Controller; use IQBall\App\Session\SessionHandle; use IQBall\App\ViewHttpResponse; +use IQBall\Core\Data\Account; use IQBall\Core\Http\HttpRequest; use IQBall\Core\Http\HttpResponse; use IQBall\Core\Model\TeamModel; @@ -107,6 +108,16 @@ class TeamController { return ViewHttpResponse::twig('display_teams.html.twig', ['teams' => $teams]); } + + public function deleteTeamByid(array $request,SessionHandle $session):HttpResponse{ + $a = $session->getAccount(); + if(isCoach($a->getEmail(),intval($request['idTeam']))){ + + } + return ; + } + + /** * @param int $id * @param SessionHandle $session diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index d775eda..925b625 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -81,5 +81,5 @@ class TeamGateway { )[0]['id'] ?? null; } - + public function isCoach(string $email,int $idTeam): } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index f6af837..569b181 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -79,4 +79,7 @@ class TeamModel { return $teamId; } + public function isCoach($email,$idTeam): bool{ + + } } -- 2.36.3 From 1914671699aaed8284510769329b231fda31833f Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 4 Dec 2023 17:15:07 +0100 Subject: [PATCH 02/22] delete team's action almost done --- public/index.php | 1 + src/App/Controller/TeamController.php | 14 ++++++--- src/App/Views/display_team.html.twig | 17 ++++++++-- src/App/Views/display_teams.html.twig | 6 ++-- src/Core/Gateway/TeamGateway.php | 45 ++++++++++++++++++++------- src/Core/Model/TeamModel.php | 10 +++++- 6 files changed, 70 insertions(+), 23 deletions(-) diff --git a/public/index.php b/public/index.php index c31e289..952e215 100644 --- a/public/index.php +++ b/public/index.php @@ -96,6 +96,7 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->displayListTeamByName($s))); $ar->map("POST", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->listTeamByName($_POST, $s))); $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); + $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(SessionHandle $s) => getTeamController()->deleteTeamByid($_POST, $s))); $ar->map("GET", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->displayAddMember($s))); $ar->map("POST", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->addMember($_POST, $s))); $ar->map("GET", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->displayDeleteMember($s))); diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index e90ae67..748594a 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -108,16 +108,20 @@ class TeamController { return ViewHttpResponse::twig('display_teams.html.twig', ['teams' => $teams]); } - + /** + * @param array $request + * @param SessionHandle $session + * @return HttpResponse + */ public function deleteTeamByid(array $request,SessionHandle $session):HttpResponse{ $a = $session->getAccount(); - if(isCoach($a->getEmail(),intval($request['idTeam']))){ - + $ret = $this->model->deleteTeam($a->getEmail(),intval($request['idTeam'])); + if($ret != 0){ + return ViewHttpResponse::twig('display_team.html.twig',['notDeleted' => true]); } - return ; + return ViewHttpResponse::redirect('home.twig'); } - /** * @param int $id * @param SessionHandle $session diff --git a/src/App/Views/display_team.html.twig b/src/App/Views/display_team.html.twig index 7f23b8b..2a3f9ab 100644 --- a/src/App/Views/display_team.html.twig +++ b/src/App/Views/display_team.html.twig @@ -53,6 +53,11 @@ width: 80px; } + #delete{ + border-radius:10px ; + background-color: red; + color: white; + } @@ -61,7 +66,7 @@
- +{% if team is defined %}

{{ team.getInfo().getName() }}

@@ -75,7 +80,9 @@
- + {% if %} + + {% endif %} {% for m in team.listMembers() %}

{{ m.getUserId() }}

{% if m.getRole().isCoach() %} @@ -85,7 +92,11 @@ {% endif %} {% endfor %} - +{% else %} +
+

Cette équipe ne peut être affichée

+
+{% endif %}
\ No newline at end of file diff --git a/src/App/Views/display_teams.html.twig b/src/App/Views/display_teams.html.twig index 1e1420a..3713265 100644 --- a/src/App/Views/display_teams.html.twig +++ b/src/App/Views/display_teams.html.twig @@ -22,9 +22,9 @@ {% else %} {% for t in teams %} -
-

Nom de l'équipe : {{ t.name }}

- logo de l'équipe +
+

Nom de l'équipe : {{ t.getName() }}

+ logo de l'équipe
{% endfor %} {% endif %} diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 925b625..a827b72 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -34,7 +34,6 @@ class TeamGateway { return intval($this->con->lastInsertId()); } - /** * @param string $name * @return TeamInfo[] @@ -56,11 +55,11 @@ class TeamGateway { */ public function getTeamById(int $id): ?TeamInfo { $row = $this->con->fetch( - "SELECT * FROM Team WHERE id = :id", - [ - ":id" => [$id, PDO::PARAM_INT], - ] - )[0] ?? null; + "SELECT * FROM Team WHERE id = :id", + [ + ":id" => [$id, PDO::PARAM_INT], + ] + )[0] ?? null; if ($row == null) { return null; } @@ -74,12 +73,36 @@ class TeamGateway { */ public function getTeamIdByName(string $name): ?int { return $this->con->fetch( - "SELECT id FROM Team WHERE name = :name", + "SELECT id FROM Team WHERE name = :name", + [ + ":name" => [$name, PDO::PARAM_INT], + ] + )[0]['id'] ?? null; + } + + public function isCoach(string $email, int $idTeam): ?string { + return $this->con->fetch( + "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", + [ + "team" => [$idTeam, PDO::PARAM_INT], + "email" => [$email, PDO::PARAM_STR] + ] + )[0]['role'] ?? null; + + } + + public function deleteTeam(int $idTeam): void { + $this->con->exec( + "DELETE FROM Member WHERE id_team=:team", + [ + "team" => [$idTeam, PDO::PARAM_INT] + ] + ); + $this->con->exec( + "DELETE FROM TEAM WHERE id=:team", [ - ":name" => [$name, PDO::PARAM_INT], + "team" => [$idTeam, PDO::PARAM_INT] ] - )[0]['id'] ?? null; + ); } - - public function isCoach(string $email,int $idTeam): } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 569b181..fb31635 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -79,7 +79,15 @@ class TeamModel { return $teamId; } - public function isCoach($email,$idTeam): bool{ + public function deleteTeam(string $email, int $idTeam): int{ + if($this->isCoach($email,$idTeam) == "Coach" ){ + $this->teams->deleteTeam($idTeam); + return 0; + } + return -1; + } + public function isCoach(string $email,int $idTeam): bool{ + return $this->teams->isCoach($email,$idTeam) == 'Coach' ; } } -- 2.36.3 From fbe31a4de9304715c6e3f2801738ba10c47f53bd Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 4 Dec 2023 18:33:35 +0100 Subject: [PATCH 03/22] added some css --- src/App/Views/display_team.html.twig | 5 ++++ src/App/Views/display_teams.html.twig | 35 +++++++++++++++++++++-- src/App/Views/list_team_by_name.html.twig | 4 ++- src/Core/Gateway/TeamGateway.php | 1 - 4 files changed, 40 insertions(+), 5 deletions(-) diff --git a/src/App/Views/display_team.html.twig b/src/App/Views/display_team.html.twig index 2a3f9ab..905e3c5 100644 --- a/src/App/Views/display_team.html.twig +++ b/src/App/Views/display_team.html.twig @@ -66,6 +66,11 @@
+ {% if notDeleted %} + +

Cette équipe ne peut être supprimée.

+
+ {% endif %} {% if team is defined %}
diff --git a/src/App/Views/display_teams.html.twig b/src/App/Views/display_teams.html.twig index 3713265..4c17a5e 100644 --- a/src/App/Views/display_teams.html.twig +++ b/src/App/Views/display_teams.html.twig @@ -3,9 +3,38 @@ Twig view + - +
+

IQBall

+
+
{% if teams is empty %}

Aucune équipe n'a été trouvée

@@ -24,10 +53,10 @@ {% for t in teams %}

Nom de l'équipe : {{ t.getName() }}

- logo de l'équipe + logo de l'équipe
{% endfor %} {% endif %} - +
\ No newline at end of file diff --git a/src/App/Views/list_team_by_name.html.twig b/src/App/Views/list_team_by_name.html.twig index eca5e19..3b93f94 100644 --- a/src/App/Views/list_team_by_name.html.twig +++ b/src/App/Views/list_team_by_name.html.twig @@ -56,7 +56,9 @@ - +
+

IQBall

+

Chercher une équipe

diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index a827b72..11735c2 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -63,7 +63,6 @@ class TeamGateway { if ($row == null) { return null; } - return new TeamInfo($row['id'], $row['name'], $row['picture'], Color::from($row['main_color']), Color::from($row['second_color'])); } -- 2.36.3 From 66aaf0c8fb72f11bbeff242ac66b42eab29f1adf Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Tue, 5 Dec 2023 17:29:13 +0100 Subject: [PATCH 04/22] add fonctional delete action, some more css, and repaired getmembersofteambyid --- public/index.php | 2 +- src/App/Controller/TeamController.php | 12 ++++---- src/App/Views/display_team.html.twig | 35 +++++++++++------------ src/App/Views/display_teams.html.twig | 1 - src/App/Views/list_team_by_name.html.twig | 3 ++ src/Core/Gateway/MemberGateway.php | 4 +-- src/Core/Gateway/TeamGateway.php | 7 ++--- src/Core/Model/TeamModel.php | 11 +++---- 8 files changed, 36 insertions(+), 39 deletions(-) diff --git a/public/index.php b/public/index.php index 952e215..278e7f1 100644 --- a/public/index.php +++ b/public/index.php @@ -96,7 +96,7 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->displayListTeamByName($s))); $ar->map("POST", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->listTeamByName($_POST, $s))); $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); - $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(SessionHandle $s) => getTeamController()->deleteTeamByid($_POST, $s))); + $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamByid($id,$s))); $ar->map("GET", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->displayAddMember($s))); $ar->map("POST", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->addMember($_POST, $s))); $ar->map("GET", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->displayDeleteMember($s))); diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 748594a..01fdb14 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -71,6 +71,7 @@ class TeamController { return ViewHttpResponse::twig('insert_team.html.twig', ['bad_fields' => $badFields]); } $teamId = $this->model->createTeam($request['name'], $request['picture'], $request['main_color'], $request['second_color']); + $this->model->addMember($session->getAccount()->getEmail(),$teamId,'Coach'); return $this->displayTeam($teamId, $session); } @@ -99,7 +100,7 @@ class TeamController { return ViewHttpResponse::twig('list_team_by_name.html.twig', ['bad_field' => $badField]); } - $teams = $this->model->listByName($request['name']); + $teams = $this->model->listByName($request['name'],$session->getAccount()->getId()); if (empty($teams)) { return ViewHttpResponse::twig('display_teams.html.twig', []); @@ -109,17 +110,17 @@ class TeamController { } /** - * @param array $request + * @param int $id * @param SessionHandle $session * @return HttpResponse */ - public function deleteTeamByid(array $request,SessionHandle $session):HttpResponse{ + public function deleteTeamByid(int $id,SessionHandle $session):HttpResponse{ $a = $session->getAccount(); - $ret = $this->model->deleteTeam($a->getEmail(),intval($request['idTeam'])); + $ret = $this->model->deleteTeam($a->getEmail(),$id); if($ret != 0){ return ViewHttpResponse::twig('display_team.html.twig',['notDeleted' => true]); } - return ViewHttpResponse::redirect('home.twig'); + return ViewHttpResponse::redirect('/'); } /** @@ -164,7 +165,6 @@ class TeamController { "team" => [Validators::isInteger()], "email" => [Validators::email(), Validators::lenBetween(5, 256)], ]); - return $this->displayTeam($this->model->deleteMember($request['email'], intval($request['team'])), $session); } } diff --git a/src/App/Views/display_team.html.twig b/src/App/Views/display_team.html.twig index 905e3c5..d013865 100644 --- a/src/App/Views/display_team.html.twig +++ b/src/App/Views/display_team.html.twig @@ -11,10 +11,6 @@ align-items: center; } - section { - width: 60%; - } - .square { width: 50px; height: 50px; @@ -30,19 +26,17 @@ border: solid; } - .container { + section { background-color: #fff; display: flex; flex-direction: column; align-items: center; + width: 60%; } - .team { - border-color: darkgrey; - border-radius: 20px; - + #colors{ + flex-direction: row; } - .color { flex-direction: row; justify-content: space-between; @@ -58,6 +52,11 @@ background-color: red; color: white; } + + .player{ + flex-direction: row; + justify-content: space-evenly; + } @@ -72,12 +71,12 @@ {% endif %} {% if team is defined %} -
+

{{ team.getInfo().getName() }}

-
+

Couleur principale :

@@ -85,16 +84,16 @@
- {% if %} - {% endif %} {% for m in team.listMembers() %} -

{{ m.getUserId() }}

- {% if m.getRole().isCoach() %} +
+

{{ m.getUserId() }}

+ {% if m.getRole().isCoach() %}

: Coach

- {% else %} + {% else %}

: Joueur

- {% endif %} + {% endif %} +
{% endfor %}
{% else %} diff --git a/src/App/Views/display_teams.html.twig b/src/App/Views/display_teams.html.twig index 4c17a5e..3e3ab12 100644 --- a/src/App/Views/display_teams.html.twig +++ b/src/App/Views/display_teams.html.twig @@ -10,7 +10,6 @@ background-color: #f1f1f1; align-items: center; } - section{ flex-direction: row; justify-content: space-around; diff --git a/src/App/Views/list_team_by_name.html.twig b/src/App/Views/list_team_by_name.html.twig index 3b93f94..092a149 100644 --- a/src/App/Views/list_team_by_name.html.twig +++ b/src/App/Views/list_team_by_name.html.twig @@ -7,6 +7,9 @@ body { font-family: Arial, sans-serif; background-color: #f1f1f1; + display: flex; + flex-direction: column; + align-items: center; } .container { diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index 999bf10..4c8bb8a 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -41,13 +41,13 @@ class MemberGateway { */ public function getMembersOfTeam(int $teamId): array { $rows = $this->con->fetch( - "SELECT a.id,m.role,a.email,a.username FROM Account a,Team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", + "SELECT a.id,m.role FROM Account a,Team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", [ ":id" => [$teamId, PDO::PARAM_INT], ] ); - return array_map(fn($row) => new Member($row['id_user'], $row['id_team'], MemberRole::fromName($row['role'])), $rows); + return array_map(fn($row) => new Member($row['id'], $teamId, MemberRole::fromName($row['role'])), $rows); } /** diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 11735c2..ba882a6 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -38,14 +38,14 @@ class TeamGateway { * @param string $name * @return TeamInfo[] */ - public function listByName(string $name): array { + public function listByName(string $name,int $id): array { $result = $this->con->fetch( - "SELECT * FROM Team WHERE name LIKE '%' || :name || '%'", + "SELECT t.* FROM Team t, Member m WHERE t.name LIKE '%' || :name || '%' AND t.id=m.id_team AND m.id_user=:id", [ ":name" => [$name, PDO::PARAM_STR], + "id" => [$id, PDO::PARAM_INT] ] ); - return array_map(fn($row) => new TeamInfo($row['id'], $row['name'], $row['picture'], Color::from($row['main_color']), Color::from($row['second_color'])), $result); } @@ -87,7 +87,6 @@ class TeamGateway { "email" => [$email, PDO::PARAM_STR] ] )[0]['role'] ?? null; - } public function deleteTeam(int $idTeam): void { diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index fb31635..0661206 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -52,8 +52,8 @@ class TeamModel { * @param string $name * @return TeamInfo[] */ - public function listByName(string $name): array { - return $this->teams->listByName($name); + public function listByName(string $name,int $id): array { + return $this->teams->listByName($name,$id); } /** @@ -66,7 +66,6 @@ class TeamModel { return new Team($teamInfo, $members); } - /** * delete a member from given team identifier * @param string $mail @@ -80,14 +79,12 @@ class TeamModel { } public function deleteTeam(string $email, int $idTeam): int{ - if($this->isCoach($email,$idTeam) == "Coach" ){ + if($this->teams->isCoach($email,$idTeam) == "Coach" ){ $this->teams->deleteTeam($idTeam); return 0; } return -1; } - public function isCoach(string $email,int $idTeam): bool{ - return $this->teams->isCoach($email,$idTeam) == 'Coach' ; - } + } -- 2.36.3 From 14968b773d91b80239cae64f1f1f644c1d18cbed Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 11 Dec 2023 09:48:16 +0100 Subject: [PATCH 05/22] added different default color in teams insertion form, display a team where you are not in is now forbidden --- sql/setup-tables.sql | 2 +- src/App/Controller/TeamController.php | 15 +++++++++++++-- src/App/Views/insert_team.html.twig | 2 +- src/Core/Gateway/MemberGateway.php | 20 ++++++++++++++++++++ src/Core/Gateway/TeamGateway.php | 11 ++--------- src/Core/Model/TeamModel.php | 16 ++++++++++------ 6 files changed, 47 insertions(+), 19 deletions(-) diff --git a/sql/setup-tables.sql b/sql/setup-tables.sql index 7c012eb..ebde8b2 100644 --- a/sql/setup-tables.sql +++ b/sql/setup-tables.sql @@ -10,7 +10,7 @@ CREATE TABLE Account email varchar UNIQUE NOT NULL, username varchar NOT NULL, token varchar UNIQUE NOT NULL, - hash varchar NOT NULL + hash varchar NOT NULL, ); CREATE TABLE Tactic diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 01fdb14..01538f6 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -5,10 +5,12 @@ namespace IQBall\App\Controller; use IQBall\App\Session\SessionHandle; use IQBall\App\ViewHttpResponse; use IQBall\Core\Data\Account; +use IQBall\Core\Http\HttpCodes; use IQBall\Core\Http\HttpRequest; use IQBall\Core\Http\HttpResponse; use IQBall\Core\Model\TeamModel; use IQBall\Core\Validation\FieldValidationFail; +use IQBall\Core\Validation\ValidationFail; use IQBall\Core\Validation\Validators; class TeamController { @@ -129,8 +131,15 @@ class TeamController { * @return ViewHttpResponse a view that displays given team information */ public function displayTeam(int $id, SessionHandle $session): ViewHttpResponse { - $result = $this->model->getTeam($id); - return ViewHttpResponse::twig('display_team.html.twig', ['team' => $result]); + $result = $this->model->getTeam($id,$session->getAccount()->getId()); + if($result == null){ + return ViewHttpResponse::twig('error.html.twig', [ + 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette équipe.")], + ], HttpCodes::FORBIDDEN); + } + else{ + return ViewHttpResponse::twig('display_team.html.twig', ['team' => $result]); + } } /** @@ -167,4 +176,6 @@ class TeamController { ]); return $this->displayTeam($this->model->deleteMember($request['email'], intval($request['team'])), $session); } + + } diff --git a/src/App/Views/insert_team.html.twig b/src/App/Views/insert_team.html.twig index 65cd096..9f4694b 100644 --- a/src/App/Views/insert_team.html.twig +++ b/src/App/Views/insert_team.html.twig @@ -68,7 +68,7 @@ - +
diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index 4c8bb8a..c82281b 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -66,4 +66,24 @@ class MemberGateway { ); } + public function isCoach(string $email, int $idTeam): ?string { + return $this->con->fetch( + "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", + [ + "team" => [$idTeam, PDO::PARAM_INT], + "email" => [$email, PDO::PARAM_STR] + ] + )[0]['role'] ?? null; + } + + public function isMemberOfTeam(int $idTeam,int $idCurrentUser): ?int { + return $this->con->fetch( + "SELECT id_user FROM Member WHERE id_team = :team AND id_user = :user", + [ + "team" => [$idTeam, PDO::PARAM_INT], + "user" => [$idCurrentUser, PDO::PARAM_INT] + ] + )[0]['idUser'] ?? null; + } + } diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index ba882a6..240aa40 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -79,15 +79,7 @@ class TeamGateway { )[0]['id'] ?? null; } - public function isCoach(string $email, int $idTeam): ?string { - return $this->con->fetch( - "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", - [ - "team" => [$idTeam, PDO::PARAM_INT], - "email" => [$email, PDO::PARAM_STR] - ] - )[0]['role'] ?? null; - } + public function deleteTeam(int $idTeam): void { $this->con->exec( @@ -103,4 +95,5 @@ class TeamGateway { ] ); } + } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 0661206..09f52cd 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -57,12 +57,16 @@ class TeamModel { } /** - * @param int $id - * @return Team + * @param int $idTeam + * @param int $idCurrentUser + * @return ?Team */ - public function getTeam(int $id): Team { - $teamInfo = $this->teams->getTeamById($id); - $members = $this->members->getMembersOfTeam($id); + public function getTeam(int $idTeam, int $idCurrentUser): ?Team { + if($this->members->isMemberOfTeam($idTeam,$idCurrentUser) == null){ + return null; + } + $teamInfo = $this->teams->getTeamById($idTeam); + $members = $this->members->getMembersOfTeam($idTeam); return new Team($teamInfo, $members); } @@ -79,7 +83,7 @@ class TeamModel { } public function deleteTeam(string $email, int $idTeam): int{ - if($this->teams->isCoach($email,$idTeam) == "Coach" ){ + if($this->members->isCoach($email,$idTeam) == "Coach" ){ $this->teams->deleteTeam($idTeam); return 0; } -- 2.36.3 From 6848d56244fd9b70e1ca0aab83571abc0831a21d Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 11 Dec 2023 17:18:46 +0100 Subject: [PATCH 06/22] fixed delete team bugs, added a pop up, starting to translate the team panel in react, starting edit team action --- front/style/teamPanel.css | 47 +++++++++++++++++++++++++++ front/views/TeamPanel.tsx | 32 ++++++++++++++++++ src/App/Controller/TeamController.php | 5 ++- src/App/Views/display_team.html.twig | 5 ++- src/App/Views/insert_team.html.twig | 1 - src/Core/Gateway/MemberGateway.php | 25 ++++++++++---- src/Core/Gateway/TeamGateway.php | 5 ++- src/Core/Model/TeamModel.php | 10 ++++-- 8 files changed, 113 insertions(+), 17 deletions(-) create mode 100644 front/style/teamPanel.css create mode 100644 front/views/TeamPanel.tsx diff --git a/front/style/teamPanel.css b/front/style/teamPanel.css new file mode 100644 index 0000000..d766e76 --- /dev/null +++ b/front/style/teamPanel.css @@ -0,0 +1,47 @@ +body { + background-color: #f1f1f1; + display: flex; + flex-direction: column; + align-items: center; +} + +.square { + width: 50px; + height: 50px; +} + +#main_color { + border: solid; +} + +section { + background-color: #fff; + display: flex; + flex-direction: column; + align-items: center; + width: 60%; +} + +#colors{ + flex-direction: row; +} +.color { + flex-direction: row; + justify-content: space-between; +} + +.logo { + height: 80px; + width: 80px; +} + +#delete{ + border-radius:10px ; + background-color: red; + color: white; +} + +.player{ + flex-direction: row; + justify-content: space-evenly; +} diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx new file mode 100644 index 0000000..ae116ce --- /dev/null +++ b/front/views/TeamPanel.tsx @@ -0,0 +1,32 @@ + +import '../style/teamPanel.css' + + +interface TeamInfo{ + id: number + name: string + picture: string + mainColor: string + secondColor: string +} + +interface Team { + info: TeamInfo + members: Member[] +} + +interface Member{ + id: number + + role: string +} + + +export default function TeamPanel({isCoach}: {isCoach: boolean}){ + + return

prout ({isCoach ? "vrai" : "faux"})

+} + + + + diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 01538f6..46adc07 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -138,7 +138,8 @@ class TeamController { ], HttpCodes::FORBIDDEN); } else{ - return ViewHttpResponse::twig('display_team.html.twig', ['team' => $result]); + $role = $this->model->isCoach($id,$session->getAccount()->getEmail()); + return ViewHttpResponse::react('views/TeamPanel.tsx', ['team' => ["a" => "b"], 'isCoach' => $role]); } } @@ -169,7 +170,6 @@ class TeamController { */ public function deleteMember(array $request, SessionHandle $session): HttpResponse { $errors = []; - $request = HttpRequest::from($request, $errors, [ "team" => [Validators::isInteger()], "email" => [Validators::email(), Validators::lenBetween(5, 256)], @@ -177,5 +177,4 @@ class TeamController { return $this->displayTeam($this->model->deleteMember($request['email'], intval($request['team'])), $session); } - } diff --git a/src/App/Views/display_team.html.twig b/src/App/Views/display_team.html.twig index d013865..8928e84 100644 --- a/src/App/Views/display_team.html.twig +++ b/src/App/Views/display_team.html.twig @@ -84,7 +84,10 @@
- + {% if isCoach %} + + + {% endif %} {% for m in team.listMembers() %}

{{ m.getUserId() }}

diff --git a/src/App/Views/insert_team.html.twig b/src/App/Views/insert_team.html.twig index 9f4694b..0c10114 100644 --- a/src/App/Views/insert_team.html.twig +++ b/src/App/Views/insert_team.html.twig @@ -54,7 +54,6 @@ background-color: #0056b3; } - diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index c82281b..91dcf43 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -66,24 +66,37 @@ class MemberGateway { ); } - public function isCoach(string $email, int $idTeam): ?string { - return $this->con->fetch( + /** + * @param string $email + * @param int $idTeam + * @return bool + */ + public function isCoach(string $email, int $idTeam): bool { + $result = $this->con->fetch( "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", [ "team" => [$idTeam, PDO::PARAM_INT], "email" => [$email, PDO::PARAM_STR] ] - )[0]['role'] ?? null; + )[0]['role']; + return $result == 'Coach'; } - public function isMemberOfTeam(int $idTeam,int $idCurrentUser): ?int { - return $this->con->fetch( + /** + * @param int $idTeam + * @param int $idCurrentUser + * @return bool + */ + public function isMemberOfTeam(int $idTeam,int $idCurrentUser): bool { + $result = $this->con->fetch( "SELECT id_user FROM Member WHERE id_team = :team AND id_user = :user", [ "team" => [$idTeam, PDO::PARAM_INT], "user" => [$idCurrentUser, PDO::PARAM_INT] ] - )[0]['idUser'] ?? null; + )[0]['id_user'] ?? null; + return $result == null; } + } diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 240aa40..5478968 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -36,6 +36,7 @@ class TeamGateway { /** * @param string $name + * @param int $id * @return TeamInfo[] */ public function listByName(string $name,int $id): array { @@ -51,7 +52,7 @@ class TeamGateway { /** * @param int $id - * @return TeamInfo + * @return ?TeamInfo */ public function getTeamById(int $id): ?TeamInfo { $row = $this->con->fetch( @@ -79,8 +80,6 @@ class TeamGateway { )[0]['id'] ?? null; } - - public function deleteTeam(int $idTeam): void { $this->con->exec( "DELETE FROM Member WHERE id_team=:team", diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 09f52cd..260da3a 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -50,6 +50,7 @@ class TeamModel { /** * @param string $name + * @param int $id * @return TeamInfo[] */ public function listByName(string $name,int $id): array { @@ -62,7 +63,7 @@ class TeamModel { * @return ?Team */ public function getTeam(int $idTeam, int $idCurrentUser): ?Team { - if($this->members->isMemberOfTeam($idTeam,$idCurrentUser) == null){ + if($this->members->isMemberOfTeam($idTeam,$idCurrentUser)){ return null; } $teamInfo = $this->teams->getTeamById($idTeam); @@ -83,12 +84,15 @@ class TeamModel { } public function deleteTeam(string $email, int $idTeam): int{ - if($this->members->isCoach($email,$idTeam) == "Coach" ){ + $this->members->isCoach($email,$idTeam); + if($this->members->isCoach($email,$idTeam)){ $this->teams->deleteTeam($idTeam); return 0; } return -1; } - + public function isCoach(int $idTeam, string $email): bool{ + return $this->members->isCoach($email,$idTeam); + } } -- 2.36.3 From edf9e9aa1cfa478dbb6c295ee1e089c70aebf69d Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 18 Dec 2023 17:26:40 +0100 Subject: [PATCH 07/22] rebased the branch + continue to translate html.twig to react --- front/views/TeamPanel.tsx | 27 ++++++++++++++++++++++++--- src/App/Controller/TeamController.php | 7 ++++++- 2 files changed, 30 insertions(+), 4 deletions(-) diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index ae116ce..c7f1a3d 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -22,11 +22,32 @@ interface Member{ } -export default function TeamPanel({isCoach}: {isCoach: boolean}){ - - return

prout ({isCoach ? "vrai" : "faux"})

+export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team }){ + return ( +
+ +
+) } +function TeamDisplay({name,picture,mainColor,secondColor}: {name: string,picture : string,mainColor}) { + return ( +
+

{name}

+ +
+
+ +
+ ) +} +function Color({color}: {color : string}){ + return( +

Couleur principale :

+
+
+ ) +} diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 46adc07..8e32498 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -139,7 +139,12 @@ class TeamController { } else{ $role = $this->model->isCoach($id,$session->getAccount()->getEmail()); - return ViewHttpResponse::react('views/TeamPanel.tsx', ['team' => ["a" => "b"], 'isCoach' => $role]); + return ViewHttpResponse::react('views/TeamPanel.tsx', [ + 'team' => [ + "info" => [ + "id" => 1 + ] + ], 'isCoach' => $role]); } } -- 2.36.3 From 18eda07d2cf9fd41ab4634268d38726bacbcc1ef Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 18 Dec 2023 23:00:14 +0100 Subject: [PATCH 08/22] continuing the translation of the team's view into react --- front/views/TeamPanel.tsx | 53 +++++++++++++++++++++++++++++++-------- 1 file changed, 42 insertions(+), 11 deletions(-) diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index c7f1a3d..81094ce 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -1,7 +1,5 @@ - import '../style/teamPanel.css' - interface TeamInfo{ id: number name: string @@ -17,7 +15,9 @@ interface Team { interface Member{ id: number - + name: string + mail: string + profilePicture: string role: string } @@ -25,19 +25,31 @@ interface Member{ export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team }){ return (
- +
+ +
+
+ {isCoach ? () : ()} +
+
+

Membres :

+ +
) } -function TeamDisplay({name,picture,mainColor,secondColor}: {name: string,picture : string,mainColor}) { +function TeamDisplay({ team}: {team : TeamInfo}) { return (
-

{name}

- -
-
- +
+

{team.name}

+ Logo d'équipe +
+
+ + +
) } @@ -45,9 +57,28 @@ function TeamDisplay({name,picture,mainColor,secondColor}: {name: string,picture function Color({color}: {color : string}){ return(

Couleur principale :

-
+
) } +function CoachOptions (){ + + return ( +
+ + +
+ ) +} +function MemberDisplay({member}: {member : Member}){ + return ( +
+ Photo de profile +

{member.name}

+

{member.role}

+

{member.mail}

+
+ ) +} -- 2.36.3 From f550bd19f7983bcda56025034380d651a65a6baf Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Wed, 20 Dec 2023 09:56:01 +0100 Subject: [PATCH 09/22] all datas are displayed in react - still have to fix the css --- front/components/editor/BasketCourt.tsx | 2 +- front/components/editor/CourtPlayer.tsx | 2 +- front/components/editor/PlayerPiece.tsx | 2 +- front/model/Team/Team.ts | 28 +++++++ front/{ => model}/tactic/Ball.ts | 0 front/{ => model}/tactic/Player.ts | 0 front/{ => model}/tactic/Tactic.ts | 0 front/{ => model}/tactic/Team.tsx | 0 front/style/{teamPanel.css => team_panel.css} | 2 +- front/views/Editor.tsx | 6 +- front/views/TeamPanel.tsx | 73 ++++++++----------- public/api/index.php | 1 - public/index.php | 2 +- sql/setup-tables.sql | 1 + src/App/Controller/EditorController.php | 4 +- src/App/Controller/TeamController.php | 18 ++--- src/App/Controller/VisualizerController.php | 2 +- src/Core/Data/Account.php | 39 +++------- src/Core/Data/Color.php | 8 +- src/Core/Data/Member.php | 45 ++++++------ src/Core/Data/MemberRole.php | 68 ----------------- src/Core/Data/Team.php | 8 +- src/Core/Data/TeamInfo.php | 6 +- src/Core/Data/User.php | 73 +++++++++++++++++++ src/Core/Gateway/AccountGateway.php | 11 +-- src/Core/Gateway/MemberGateway.php | 7 +- src/Core/Gateway/TeamGateway.php | 5 +- src/Core/Model/AuthModel.php | 11 ++- src/Core/Model/TeamModel.php | 4 +- 29 files changed, 226 insertions(+), 202 deletions(-) create mode 100644 front/model/Team/Team.ts rename front/{ => model}/tactic/Ball.ts (100%) rename front/{ => model}/tactic/Player.ts (100%) rename front/{ => model}/tactic/Tactic.ts (100%) rename front/{ => model}/tactic/Team.tsx (100%) rename front/style/{teamPanel.css => team_panel.css} (92%) delete mode 100755 src/Core/Data/MemberRole.php create mode 100644 src/Core/Data/User.php diff --git a/front/components/editor/BasketCourt.tsx b/front/components/editor/BasketCourt.tsx index 6229afd..0cfcd48 100644 --- a/front/components/editor/BasketCourt.tsx +++ b/front/components/editor/BasketCourt.tsx @@ -2,7 +2,7 @@ import CourtSvg from "../../assets/basketball_court.svg?react" import "../../style/basket_court.css" import { RefObject, useRef } from "react" import CourtPlayer from "./CourtPlayer" -import { Player } from "../../tactic/Player" +import { Player } from "../../model/tactic/Player" export interface BasketCourtProps { players: Player[] diff --git a/front/components/editor/CourtPlayer.tsx b/front/components/editor/CourtPlayer.tsx index 6aebdcb..cc837e3 100644 --- a/front/components/editor/CourtPlayer.tsx +++ b/front/components/editor/CourtPlayer.tsx @@ -4,7 +4,7 @@ import RemoveIcon from "../../assets/icon/remove.svg?react" import { BallPiece } from "./BallPiece" import Draggable from "react-draggable" import { PlayerPiece } from "./PlayerPiece" -import { Player } from "../../tactic/Player" +import { Player } from "../../model/tactic/Player" import { calculateRatio } from "../../Utils" export interface PlayerProps { diff --git a/front/components/editor/PlayerPiece.tsx b/front/components/editor/PlayerPiece.tsx index e725d31..f9e1ad6 100644 --- a/front/components/editor/PlayerPiece.tsx +++ b/front/components/editor/PlayerPiece.tsx @@ -1,6 +1,6 @@ import React from "react" import "../../style/player.css" -import { Team } from "../../tactic/Team" +import { Team } from "../../model/tactic/Team" export interface PlayerPieceProps { team: Team diff --git a/front/model/Team/Team.ts b/front/model/Team/Team.ts new file mode 100644 index 0000000..99fe6dd --- /dev/null +++ b/front/model/Team/Team.ts @@ -0,0 +1,28 @@ +export interface TeamInfo{ + id: number + name: string + picture: string + mainColor: Color + secondColor: Color +} + +export interface Color{ + hex: string +} + +export interface Team { + info: TeamInfo + members: Member[] +} + +export interface Member{ + user: User + role: string +} + +export interface User{ + id: number + name: string + email: string + profilePicture: string +} \ No newline at end of file diff --git a/front/tactic/Ball.ts b/front/model/tactic/Ball.ts similarity index 100% rename from front/tactic/Ball.ts rename to front/model/tactic/Ball.ts diff --git a/front/tactic/Player.ts b/front/model/tactic/Player.ts similarity index 100% rename from front/tactic/Player.ts rename to front/model/tactic/Player.ts diff --git a/front/tactic/Tactic.ts b/front/model/tactic/Tactic.ts similarity index 100% rename from front/tactic/Tactic.ts rename to front/model/tactic/Tactic.ts diff --git a/front/tactic/Team.tsx b/front/model/tactic/Team.tsx similarity index 100% rename from front/tactic/Team.tsx rename to front/model/tactic/Team.tsx diff --git a/front/style/teamPanel.css b/front/style/team_panel.css similarity index 92% rename from front/style/teamPanel.css rename to front/style/team_panel.css index d766e76..3ff5ff7 100644 --- a/front/style/teamPanel.css +++ b/front/style/team_panel.css @@ -1,5 +1,5 @@ body { - background-color: #f1f1f1; + background-color: var(--background-color); display: flex; flex-direction: column; align-items: center; diff --git a/front/views/Editor.tsx b/front/views/Editor.tsx index 5c10f64..5adbe51 100644 --- a/front/views/Editor.tsx +++ b/front/views/Editor.tsx @@ -17,10 +17,10 @@ import { Rack } from "../components/Rack" import { PlayerPiece } from "../components/editor/PlayerPiece" import { BallPiece } from "../components/editor/BallPiece" -import { Player } from "../tactic/Player" -import { Tactic, TacticContent } from "../tactic/Tactic" +import { Player } from "../model/tactic/Player" +import { Tactic, TacticContent } from "../model/tactic/Tactic" import { fetchAPI } from "../Fetcher" -import { Team } from "../tactic/Team" +import { Team } from "../model/tactic/Team" import { calculateRatio } from "../Utils" import SavingState, { SaveState, diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 81094ce..5458b1b 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -1,42 +1,20 @@ -import '../style/teamPanel.css' - -interface TeamInfo{ - id: number - name: string - picture: string - mainColor: string - secondColor: string -} - -interface Team { - info: TeamInfo - members: Member[] -} - -interface Member{ - id: number - name: string - mail: string - profilePicture: string - role: string -} - +import '../style/team_panel.css'; +import {BASE} from "../Constants"; +import {Team,TeamInfo,Color,User,Member} from "../model/Team/Team" export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team }){ return (
-
- -
-
- {isCoach ? () : ()} -
+ + + {isCoach && } +

Membres :

- +
-) + ) } function TeamDisplay({ team}: {team : TeamInfo}) { @@ -47,27 +25,36 @@ function TeamDisplay({ team}: {team : TeamInfo}) { Logo d'équipe
- - +

Couleur principale

+ +

Couleur secondaire

+
) } -function Color({color}: {color : string}){ +function ColorDisplay({color}: {color : string}){ return( -

Couleur principale :

-
-
+
) } -function CoachOptions (){ - +function CoachOptions ({id}:{id:number}){ return (
- + +
+ ) +} +function MembersDisplay({members}:{members : Member[]}){ + const listMember = members.map((member) => + + ); + return ( +
+ {listMember}
) } @@ -75,10 +62,10 @@ function CoachOptions (){ function MemberDisplay({member}: {member : Member}){ return (
- Photo de profile -

{member.name}

+ Photo de profile +

{member.user.name}

{member.role}

-

{member.mail}

+

{member.user.email}

) } diff --git a/public/api/index.php b/public/api/index.php index 5734571..da25013 100644 --- a/public/api/index.php +++ b/public/api/index.php @@ -51,7 +51,6 @@ function tryGetAuthorization(): ?Account { $session = PhpSessionHandle::init(); return $session->getAccount(); } - $token = $headers['Authorization']; $gateway = new AccountGateway(new Connection(get_database())); return $gateway->getAccountFromToken($token); diff --git a/public/index.php b/public/index.php index 58a78a4..906a2ae 100644 --- a/public/index.php +++ b/public/index.php @@ -103,7 +103,7 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->displayListTeamByName($s))); $ar->map("POST", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->listTeamByName($_POST, $s))); $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); - $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamByid($id,$s))); + $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamById($id,$s))); $ar->map("GET", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->displayAddMember($s))); $ar->map("POST", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->addMember($_POST, $s))); $ar->map("GET", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->displayDeleteMember($s))); diff --git a/sql/setup-tables.sql b/sql/setup-tables.sql index ae5a478..0cf6734 100644 --- a/sql/setup-tables.sql +++ b/sql/setup-tables.sql @@ -11,6 +11,7 @@ CREATE TABLE Account username varchar NOT NULL, token varchar UNIQUE NOT NULL, hash varchar NOT NULL, + profilePicture varchar NOT NULL ); CREATE TABLE Tactic diff --git a/src/App/Controller/EditorController.php b/src/App/Controller/EditorController.php index 3bbbe61..a05c7d4 100644 --- a/src/App/Controller/EditorController.php +++ b/src/App/Controller/EditorController.php @@ -63,7 +63,7 @@ class EditorController { return $this->openTestEditor($type); } - $tactic = $this->model->makeNewDefault($session->getAccount()->getId(), $type); + $tactic = $this->model->makeNewDefault($session->getAccount()->getUser()->getId(), $type); return $this->openEditorFor($tactic); } @@ -76,7 +76,7 @@ class EditorController { public function openEditor(int $id, SessionHandle $session): ViewHttpResponse { $tactic = $this->model->get($id); - $failure = TacticValidator::validateAccess($id, $tactic, $session->getAccount()->getId()); + $failure = TacticValidator::validateAccess($id, $tactic, $session->getAccount()->getUser()->getId()); if ($failure != null) { return ViewHttpResponse::twig('error.html.twig', ['failures' => [$failure]], HttpCodes::NOT_FOUND); diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 8e32498..df6188c 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -73,7 +73,7 @@ class TeamController { return ViewHttpResponse::twig('insert_team.html.twig', ['bad_fields' => $badFields]); } $teamId = $this->model->createTeam($request['name'], $request['picture'], $request['main_color'], $request['second_color']); - $this->model->addMember($session->getAccount()->getEmail(),$teamId,'Coach'); + $this->model->addMember($session->getAccount()->getUser()->getEmail(),$teamId,'COACH'); return $this->displayTeam($teamId, $session); } @@ -102,12 +102,11 @@ class TeamController { return ViewHttpResponse::twig('list_team_by_name.html.twig', ['bad_field' => $badField]); } - $teams = $this->model->listByName($request['name'],$session->getAccount()->getId()); + $teams = $this->model->listByName($request['name'],$session->getAccount()->getUser()->getId()); if (empty($teams)) { return ViewHttpResponse::twig('display_teams.html.twig', []); } - return ViewHttpResponse::twig('display_teams.html.twig', ['teams' => $teams]); } @@ -116,9 +115,9 @@ class TeamController { * @param SessionHandle $session * @return HttpResponse */ - public function deleteTeamByid(int $id,SessionHandle $session):HttpResponse{ + public function deleteTeamById(int $id, SessionHandle $session):HttpResponse{ $a = $session->getAccount(); - $ret = $this->model->deleteTeam($a->getEmail(),$id); + $ret = $this->model->deleteTeam($a->getUser()->getEmail(),$id); if($ret != 0){ return ViewHttpResponse::twig('display_team.html.twig',['notDeleted' => true]); } @@ -131,19 +130,18 @@ class TeamController { * @return ViewHttpResponse a view that displays given team information */ public function displayTeam(int $id, SessionHandle $session): ViewHttpResponse { - $result = $this->model->getTeam($id,$session->getAccount()->getId()); + $result = $this->model->getTeam($id,$session->getAccount()->getUser()->getId()); if($result == null){ return ViewHttpResponse::twig('error.html.twig', [ 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette équipe.")], ], HttpCodes::FORBIDDEN); } else{ - $role = $this->model->isCoach($id,$session->getAccount()->getEmail()); + $role = $this->model->isCoach($id,$session->getAccount()->getUser()->getEmail()); return ViewHttpResponse::react('views/TeamPanel.tsx', [ 'team' => [ - "info" => [ - "id" => 1 - ] + "info" => $result->getInfo(), + "members" => $result->listMembers() ], 'isCoach' => $role]); } } diff --git a/src/App/Controller/VisualizerController.php b/src/App/Controller/VisualizerController.php index 631468e..946f6d0 100644 --- a/src/App/Controller/VisualizerController.php +++ b/src/App/Controller/VisualizerController.php @@ -28,7 +28,7 @@ class VisualizerController { public function openVisualizer(int $id, SessionHandle $session): HttpResponse { $tactic = $this->tacticModel->get($id); - $failure = TacticValidator::validateAccess($id, $tactic, $session->getAccount()->getId()); + $failure = TacticValidator::validateAccess($id, $tactic, $session->getAccount()->getUser()->getId()); if ($failure != null) { return ViewHttpResponse::twig('error.html.twig', ['failures' => [$failure]], HttpCodes::NOT_FOUND); diff --git a/src/Core/Data/Account.php b/src/Core/Data/Account.php index 48b3e69..01be656 100755 --- a/src/Core/Data/Account.php +++ b/src/Core/Data/Account.php @@ -8,10 +8,6 @@ namespace IQBall\Core\Data; * to share to other users, or non-needed public information */ class Account { - /** - * @var string $email account's mail address - */ - private string $email; /** * @var string string token @@ -19,43 +15,28 @@ class Account { private string $token; /** - * @var string the account's username - */ - private string $name; - - /** - * @var int + * @var User contains all the account's "public" information */ - private int $id; - + private User $user; /** - * @param string $email - * @param string $name * @param string $token - * @param int $id + * @param User $user */ - public function __construct(string $email, string $name, string $token, int $id) { - $this->email = $email; - $this->name = $name; + public function __construct(string $token, User $user) { $this->token = $token; - $this->id = $id; - } - - public function getId(): int { - return $this->id; - } - - public function getEmail(): string { - return $this->email; + $this->user = $user; } public function getToken(): string { return $this->token; } - public function getName(): string { - return $this->name; + /** + * @return User + */ + public function getUser(): User { + return $this->user; } } diff --git a/src/Core/Data/Color.php b/src/Core/Data/Color.php index e0cd27c..8cb07a5 100755 --- a/src/Core/Data/Color.php +++ b/src/Core/Data/Color.php @@ -4,7 +4,7 @@ namespace IQBall\Core\Data; use InvalidArgumentException; -class Color { +class Color implements \JsonSerializable { /** * @var string that represents an hexadecimal color code */ @@ -41,4 +41,10 @@ class Color { } return new Color($value); } + + public function jsonSerialize() { + return get_object_vars($this); + } + + } diff --git a/src/Core/Data/Member.php b/src/Core/Data/Member.php index d68140c..37f8f04 100755 --- a/src/Core/Data/Member.php +++ b/src/Core/Data/Member.php @@ -5,11 +5,9 @@ namespace IQBall\Core\Data; /** * information about a team member */ -class Member { - /** - * @var int The member's user account - */ - private int $userId; +class Member implements \JsonSerializable { + + private User $user; /** * @var int The member's team id @@ -17,32 +15,25 @@ class Member { private int $teamId; /** - * @var MemberRole the member's role + * @var string the member's role */ - private MemberRole $role; + private string $role; /** - * @param int $userId - * @param MemberRole $role + * @param User $user + * @param int $teamId + * @param string $role */ - public function __construct(int $userId, int $teamId, MemberRole $role) { - $this->userId = $userId; + public function __construct(User $user, int $teamId, string $role) { + $this->user = $user; $this->teamId = $teamId; $this->role = $role; } - - /** - * @return int - */ - public function getUserId(): int { - return $this->userId; - } - /** - * @return MemberRole + * @return string */ - public function getRole(): MemberRole { + public function getRole(): string { return $this->role; } @@ -52,4 +43,16 @@ class Member { public function getTeamId(): int { return $this->teamId; } + + /** + * @return User + */ + public function getUser(): User { + return $this->user; + } + + + public function jsonSerialize() { + return get_object_vars($this); + } } diff --git a/src/Core/Data/MemberRole.php b/src/Core/Data/MemberRole.php deleted file mode 100755 index 9606c0b..0000000 --- a/src/Core/Data/MemberRole.php +++ /dev/null @@ -1,68 +0,0 @@ -isValid($val)) { - throw new InvalidArgumentException("Valeur du rôle invalide"); - } - $this->value = $val; - } - - public static function player(): MemberRole { - return new MemberRole(MemberRole::ROLE_PLAYER); - } - - public static function coach(): MemberRole { - return new MemberRole(MemberRole::ROLE_COACH); - } - - public function name(): string { - switch ($this->value) { - case self::ROLE_COACH: - return "COACH"; - case self::ROLE_PLAYER: - return "PLAYER"; - } - die("unreachable"); - } - - public static function fromName(string $name): ?MemberRole { - switch ($name) { - case "COACH": - return MemberRole::coach(); - case "PLAYER": - return MemberRole::player(); - default: - return null; - } - } - - private function isValid(int $val): bool { - return ($val <= self::MAX and $val >= self::MIN); - } - - public function isPlayer(): bool { - return ($this->value == self::ROLE_PLAYER); - } - - public function isCoach(): bool { - return ($this->value == self::ROLE_COACH); - } - -} diff --git a/src/Core/Data/Team.php b/src/Core/Data/Team.php index b8e7834..7adeb49 100755 --- a/src/Core/Data/Team.php +++ b/src/Core/Data/Team.php @@ -2,7 +2,7 @@ namespace IQBall\Core\Data; -class Team { +class Team implements \JsonSerializable { private TeamInfo $info; /** @@ -29,4 +29,10 @@ class Team { public function listMembers(): array { return $this->members; } + + public function jsonSerialize() { + return get_object_vars($this); + } + + } diff --git a/src/Core/Data/TeamInfo.php b/src/Core/Data/TeamInfo.php index 7affcea..63b6a99 100644 --- a/src/Core/Data/TeamInfo.php +++ b/src/Core/Data/TeamInfo.php @@ -2,7 +2,7 @@ namespace IQBall\Core\Data; -class TeamInfo { +class TeamInfo implements \JsonSerializable { private int $id; private string $name; private string $picture; @@ -45,5 +45,9 @@ class TeamInfo { return $this->secondColor; } + public function jsonSerialize() { + return get_object_vars($this); + } + } diff --git a/src/Core/Data/User.php b/src/Core/Data/User.php new file mode 100644 index 0000000..b1fdd22 --- /dev/null +++ b/src/Core/Data/User.php @@ -0,0 +1,73 @@ +email = $email; + $this->name = $name; + $this->id = $id; + $this->profilePicture = $profilePicture; + } + + /** + * @return string + */ + public function getEmail(): string { + return $this->email; + } + + /** + * @return string + */ + public function getName(): string { + return $this->name; + } + + /** + * @return int + */ + public function getId(): int { + return $this->id; + } + + /** + * @return string + */ + public function getProfilePicture(): string { + return $this->profilePicture; + } + + public function jsonSerialize() { + return get_object_vars($this); + } +} \ No newline at end of file diff --git a/src/Core/Gateway/AccountGateway.php b/src/Core/Gateway/AccountGateway.php index 7740b57..1d109d0 100644 --- a/src/Core/Gateway/AccountGateway.php +++ b/src/Core/Gateway/AccountGateway.php @@ -4,6 +4,7 @@ namespace IQBall\Core\Gateway; use IQBall\Core\Connection; use IQBall\Core\Data\Account; +use IQBall\Core\Data\User; use PDO; class AccountGateway { @@ -16,13 +17,13 @@ class AccountGateway { $this->con = $con; } - - public function insertAccount(string $name, string $email, string $token, string $hash): int { - $this->con->exec("INSERT INTO Account(username, hash, email, token) VALUES (:username,:hash,:email,:token)", [ + public function insertAccount(string $name, string $email, string $token, string $hash,string $profilePicture): int { + $this->con->exec("INSERT INTO Account(username, hash, email, token,profilePicture) VALUES (:username,:hash,:email,:token,:profilePic)", [ ':username' => [$name, PDO::PARAM_STR], ':hash' => [$hash, PDO::PARAM_STR], ':email' => [$email, PDO::PARAM_STR], ':token' => [$token, PDO::PARAM_STR], + ':profilePic' => [$profilePicture, PDO::PARAM_STR] ]); return intval($this->con->lastInsertId()); } @@ -65,7 +66,7 @@ class AccountGateway { return null; } - return new Account($email, $acc["username"], $acc["token"], $acc["id"]); + return new Account($acc["token"],new User($email,$acc["username"],$acc["id"],$acc["profilePicture"])); } /** @@ -78,7 +79,7 @@ class AccountGateway { return null; } - return new Account($acc["email"], $acc["username"], $acc["token"], $acc["id"]); + return new Account($acc["token"],new User($acc["email"],$acc["username"],$acc["id"],$acc["profilePicture"])); } diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index 91dcf43..f9b0c3d 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -4,7 +4,7 @@ namespace IQBall\Core\Gateway; use IQBall\Core\Connection; use IQBall\Core\Data\Member; -use IQBall\Core\Data\MemberRole; +use IQBall\Core\Data\User; use PDO; class MemberGateway { @@ -41,13 +41,12 @@ class MemberGateway { */ public function getMembersOfTeam(int $teamId): array { $rows = $this->con->fetch( - "SELECT a.id,m.role FROM Account a,Team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", + "SELECT a.id,a.email,a.username,a.profilePicture,m.role FROM Account a,Team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", [ ":id" => [$teamId, PDO::PARAM_INT], ] ); - - return array_map(fn($row) => new Member($row['id'], $teamId, MemberRole::fromName($row['role'])), $rows); + return array_map(fn($row) => new Member(new User($row['email'],$row['username'],$row['id'],$row['profilePicture']), $teamId, $row['role']),$rows); } /** diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 5478968..0160e00 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -52,7 +52,7 @@ class TeamGateway { /** * @param int $id - * @return ?TeamInfo + * @return TeamInfo|null */ public function getTeamById(int $id): ?TeamInfo { $row = $this->con->fetch( @@ -80,6 +80,9 @@ class TeamGateway { )[0]['id'] ?? null; } + /** + * @param int $idTeam + */ public function deleteTeam(int $idTeam): void { $this->con->exec( "DELETE FROM Member WHERE id_team=:team", diff --git a/src/Core/Model/AuthModel.php b/src/Core/Model/AuthModel.php index e8710c0..dcf1a66 100644 --- a/src/Core/Model/AuthModel.php +++ b/src/Core/Model/AuthModel.php @@ -2,13 +2,16 @@ namespace IQBall\Core\Model; +use Exception; use IQBall\Core\Data\Account; +use IQBall\Core\Data\User; use IQBall\Core\Gateway\AccountGateway; use IQBall\Core\Validation\FieldValidationFail; use IQBall\Core\Validation\ValidationFail; class AuthModel { private AccountGateway $gateway; + private const DEFAULT_PROFILE_PICTURE = "https://cdn.pixabay.com/photo/2015/10/05/22/37/blank-profile-picture-973460_960_720.png"; /** * @param AccountGateway $gateway @@ -17,7 +20,6 @@ class AuthModel { $this->gateway = $gateway; } - /** * @param string $username * @param string $password @@ -25,6 +27,7 @@ class AuthModel { * @param string $email * @param ValidationFail[] $failures * @return Account|null the registered account or null if failures occurred + * @throws Exception */ public function register(string $username, string $password, string $confirmPassword, string $email, array &$failures): ?Account { @@ -43,13 +46,14 @@ class AuthModel { $hash = password_hash($password, PASSWORD_DEFAULT); $token = $this->generateToken(); - $accountId = $this->gateway->insertAccount($username, $email, $token, $hash); - return new Account($email, $username, $token, $accountId); + $accountId = $this->gateway->insertAccount($username, $email, $token, $hash,self::DEFAULT_PROFILE_PICTURE); + return new Account($token,new User($email,$username,$accountId,self::DEFAULT_PROFILE_PICTURE)); } /** * Generate a random base 64 string * @return string + * @throws Exception */ private function generateToken(): string { return base64_encode(random_bytes(64)); @@ -70,5 +74,4 @@ class AuthModel { return $this->gateway->getAccountFromMail($email); } - } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 260da3a..490da7b 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -44,7 +44,7 @@ class TeamModel { * @return void */ public function addMember(string $mail, int $teamId, string $role): void { - $userId = $this->users->getAccountFromMail($mail)->getId(); + $userId = $this->users->getAccountFromMail($mail)->getUser()->getId(); $this->members->insert($teamId, $userId, $role); } @@ -78,7 +78,7 @@ class TeamModel { * @return int */ public function deleteMember(string $mail, int $teamId): int { - $userId = $this->users->getAccountFromMail($mail)->getId(); + $userId = $this->users->getAccountFromMail($mail)->getUser()->getId(); $this->members->remove($teamId, $userId); return $teamId; } -- 2.36.3 From cd146477502b5b841cc8250d48fe4ea59ab28039 Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Wed, 20 Dec 2023 11:30:27 +0100 Subject: [PATCH 10/22] Translated the html.twig team's view in react and done implementing account into team --- front/style/team_panel.css | 46 ++++++++++++++++++++++++--- front/views/TeamPanel.tsx | 30 +++++++++-------- src/App/Controller/TeamController.php | 1 + src/Core/Gateway/MemberGateway.php | 3 +- 4 files changed, 60 insertions(+), 20 deletions(-) diff --git a/front/style/team_panel.css b/front/style/team_panel.css index 3ff5ff7..409ecc9 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -1,5 +1,5 @@ -body { - background-color: var(--background-color); +#mainDiv { + background-color: lightblue; display: flex; flex-direction: column; align-items: center; @@ -23,6 +23,7 @@ section { } #colors{ + display: flex; flex-direction: row; } .color { @@ -30,9 +31,11 @@ section { justify-content: space-between; } -.logo { - height: 80px; - width: 80px; +#logo { + width: 90%; + aspect-ratio: 3/2; + object-fit: contain; + mix-blend-mode: color-burn; } #delete{ @@ -45,3 +48,36 @@ section { flex-direction: row; justify-content: space-evenly; } + +#profilePicture{ + height:40px; + width:40px; +} + +#Members{ + display: flex; + flex-direction: column; + background-color: lightcoral; + width: 60%; + align-items: center; + justify-content: space-between; + +} + +.Member{ + width: 60%; + background-color: red; + display: flex; + flex-direction: row; + justify-content: space-evenly; +} + +#teamInfo{ + display: flex; + flex-direction: column; + align-items: center; + + width: 60%; + align-items: center; + background-color: #666666; +} \ No newline at end of file diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 5458b1b..e6f7166 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -4,39 +4,40 @@ import {Team,TeamInfo,Color,User,Member} from "../model/Team/Team" export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team }){ return ( -
+
+
+

IQBall

+
{isCoach && } -
-

Membres :

- -
+ +
) } function TeamDisplay({ team}: {team : TeamInfo}) { return ( -
+

{team.name}

- Logo d'équipe +

Couleur principale

- +

Couleur secondaire

- +
) } -function ColorDisplay({color}: {color : string}){ +function ColorDisplay({color}: {color : Color}){ return( -
+
) } @@ -53,7 +54,8 @@ function MembersDisplay({members}:{members : Member[]}){ ); return ( -
+
+

Membres :

{listMember}
) @@ -61,8 +63,8 @@ function MembersDisplay({members}:{members : Member[]}){ function MemberDisplay({member}: {member : Member}){ return ( -
- Photo de profile +
+ Photo de profile

{member.user.name}

{member.role}

{member.user.email}

diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index df6188c..8b85773 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -138,6 +138,7 @@ class TeamController { } else{ $role = $this->model->isCoach($id,$session->getAccount()->getUser()->getEmail()); + var_dump($role); return ViewHttpResponse::react('views/TeamPanel.tsx', [ 'team' => [ "info" => $result->getInfo(), diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index f9b0c3d..70e2032 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -78,7 +78,8 @@ class MemberGateway { "email" => [$email, PDO::PARAM_STR] ] )[0]['role']; - return $result == 'Coach'; + var_dump($result); + return $result == 'COACH'; } /** -- 2.36.3 From c0a02c91c53e1f7f74828d10e43df07d15ecdc9b Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Wed, 20 Dec 2023 15:23:10 +0100 Subject: [PATCH 11/22] implementing the add of member in a team --- front/style/team_panel.css | 42 +++++++++++++++++++++++++++ front/views/TeamPanel.tsx | 9 ++++-- public/index.php | 2 +- src/App/Controller/TeamController.php | 27 ++++++++--------- src/App/Views/add_member.html.twig | 4 +-- src/Core/Data/Color.php | 2 +- src/Core/Gateway/MemberGateway.php | 2 +- 7 files changed, 66 insertions(+), 22 deletions(-) diff --git a/front/style/team_panel.css b/front/style/team_panel.css index 409ecc9..d9104a6 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -80,4 +80,46 @@ section { width: 60%; align-items: center; background-color: #666666; +} + +#headMembers{ + width: 33%; + display: flex; + flex-direction: row; + justify-content: space-between; +} + +#addMember{ + height: 30px; + aspect-ratio: 1/1; + border-radius: 100%; + align-self: center; +} + +.popup { + display: none; + position: fixed; + top: 0; + left: 0; + width: 100%; + height: 100%; + background-color: rgba(0,0,0,0.7); +} + +.popup-content { + position: absolute; + top: 50%; + left: 50%; + transform: translate(-50%, -50%); + background-color: #fff; + padding: 20px; + text-align: center; +} + +.close { + position: absolute; + top: 10px; + right: 10px; + font-size: 20px; + cursor: pointer; } \ No newline at end of file diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index e6f7166..9b28097 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -6,7 +6,7 @@ export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team return (
-

IQBall

+

IQBall

@@ -49,13 +49,16 @@ function CoachOptions ({id}:{id:number}){ ) } -function MembersDisplay({members}:{members : Member[]}){ +function MembersDisplay({members,isCoach}:{members : Member[], isCoach : boolean}){ const listMember = members.map((member) => ); return (
-

Membres :

+
+

Membres :

+ +
{listMember}
) diff --git a/public/index.php b/public/index.php index 906a2ae..afe7cd6 100644 --- a/public/index.php +++ b/public/index.php @@ -105,7 +105,7 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamById($id,$s))); $ar->map("GET", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->displayAddMember($s))); - $ar->map("POST", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->addMember($_POST, $s))); + $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->addMember($id,$_POST, $s))); $ar->map("GET", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->displayDeleteMember($s))); $ar->map("POST", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->deleteMember($_POST, $s))); diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 8b85773..56ac482 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -32,13 +32,7 @@ class TeamController { } - /** - * @param SessionHandle $session - * @return ViewHttpResponse the team panel to add a member - */ - public function displayAddMember(SessionHandle $session): ViewHttpResponse { - return ViewHttpResponse::twig("add_member.html.twig", []); - } + /** @@ -74,7 +68,7 @@ class TeamController { } $teamId = $this->model->createTeam($request['name'], $request['picture'], $request['main_color'], $request['second_color']); $this->model->addMember($session->getAccount()->getUser()->getEmail(),$teamId,'COACH'); - return $this->displayTeam($teamId, $session); + return ViewHttpResponse::redirect('/team/'.$teamId); } /** @@ -138,7 +132,7 @@ class TeamController { } else{ $role = $this->model->isCoach($id,$session->getAccount()->getUser()->getEmail()); - var_dump($role); + return ViewHttpResponse::react('views/TeamPanel.tsx', [ 'team' => [ "info" => $result->getInfo(), @@ -147,13 +141,21 @@ class TeamController { } } + /** + * @param SessionHandle $session + * @return ViewHttpResponse the team panel to add a member + */ + public function displayAddMember(SessionHandle $session): ViewHttpResponse { + return ViewHttpResponse::twig("add_member.html.twig", []); + } + /** * add a member to a team * @param array $request * @param SessionHandle $session * @return HttpResponse */ - public function addMember(array $request, SessionHandle $session): HttpResponse { + public function addMember(int $idTeam,array $request, SessionHandle $session): HttpResponse { $errors = []; $request = HttpRequest::from($request, $errors, [ @@ -161,9 +163,8 @@ class TeamController { "email" => [Validators::email(), Validators::lenBetween(5, 256)], ]); - $teamId = intval($request['team']); - $this->model->addMember($request['email'], $teamId, $request['role']); - return $this->displayTeam($teamId, $session); + $this->model->addMember($request['email'], $idTeam, $request['role']); + return ViewHttpResponse::redirect('/team/'.$idTeam); } /** diff --git a/src/App/Views/add_member.html.twig b/src/App/Views/add_member.html.twig index c6bae0e..2cc9811 100644 --- a/src/App/Views/add_member.html.twig +++ b/src/App/Views/add_member.html.twig @@ -73,10 +73,8 @@

Ajouter un membre à votre équipe

- +
- - diff --git a/src/Core/Data/Color.php b/src/Core/Data/Color.php index 8cb07a5..f6244cd 100755 --- a/src/Core/Data/Color.php +++ b/src/Core/Data/Color.php @@ -29,7 +29,7 @@ class Color implements \JsonSerializable { public static function from(string $value): Color { $color = self::tryFrom($value); if ($color == null) { - var_dump($value); + throw new InvalidArgumentException("The string is not an hexadecimal code"); } return $color; diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index 70e2032..f14790c 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -78,7 +78,7 @@ class MemberGateway { "email" => [$email, PDO::PARAM_STR] ] )[0]['role']; - var_dump($result); + return $result == 'COACH'; } -- 2.36.3 From d2ac21a906c89c3a5196c284102db580ac0edca0 Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Thu, 21 Dec 2023 03:33:24 +0100 Subject: [PATCH 12/22] fully implemented the add of members + added style on the page + almost done implementing the remove of members --- front/style/team_panel.css | 125 ++++++++++++++------------ front/views/TeamPanel.tsx | 31 ++++--- public/index.php | 5 +- src/App/Controller/TeamController.php | 43 +++++---- src/App/Views/add_member.html.twig | 27 ++++-- src/Core/Gateway/MemberGateway.php | 6 +- src/Core/Model/TeamModel.php | 27 ++++-- 7 files changed, 154 insertions(+), 110 deletions(-) diff --git a/front/style/team_panel.css b/front/style/team_panel.css index d9104a6..935ed96 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -1,8 +1,22 @@ #mainDiv { - background-color: lightblue; display: flex; flex-direction: column; align-items: center; + height: 100%; +} + +header{ + display: flex; + justify-content: center; + background-color: #525252; + width: 100%; + margin-bottom: 5px; +} + +header h1 a{ + color: orange; + text-decoration: none; + font-size: 1.5em; } .square { @@ -14,23 +28,51 @@ border: solid; } -section { - background-color: #fff; +#teamInfo{ display: flex; flex-direction: column; align-items: center; width: 60%; + background-color: #8F8F8F; + padding-bottom: 10px; + border-radius: 10px; +} + +#firstPart{ + display: flex; + flex-direction: column; + align-items: center; +} + +#teamName{ + font-size: 2.8em; } #colors{ display: flex; - flex-direction: row; + flex-direction: column; } .color { flex-direction: row; justify-content: space-between; } +#colorsTitle{ + width: 110%; + display: flex; + flex-direction: row; + justify-content: space-between; + font-size: 1.3em; + color: white; +} + + +#actualColors{ + display: flex; + flex-direction: row; + justify-content: space-around; +} + #logo { width: 90%; aspect-ratio: 3/2; @@ -42,84 +84,49 @@ section { border-radius:10px ; background-color: red; color: white; + margin-top: 10px; + margin-bottom: 10px; } -.player{ +#headMembers{ + width: 33%; + display: flex; flex-direction: row; justify-content: space-evenly; } -#profilePicture{ - height:40px; - width:40px; +#addMember{ + height: 30px; + aspect-ratio: 1/1; + border-radius: 100%; + align-self: center; } #Members{ display: flex; flex-direction: column; - background-color: lightcoral; + background-color: #BCBCBC; width: 60%; align-items: center; - justify-content: space-between; - + justify-content: space-around; + border-radius: 10px; } .Member{ width: 60%; - background-color: red; + background-color: white; display: flex; flex-direction: row; justify-content: space-evenly; -} - -#teamInfo{ - display: flex; - flex-direction: column; align-items: center; + border-radius: 10px; + margin-top: 5px; + margin-bottom: 5px; - width: 60%; - align-items: center; - background-color: #666666; } -#headMembers{ - width: 33%; - display: flex; - flex-direction: row; - justify-content: space-between; -} - -#addMember{ - height: 30px; - aspect-ratio: 1/1; - border-radius: 100%; - align-self: center; +#profilePicture{ + height:40px; + width:40px; } -.popup { - display: none; - position: fixed; - top: 0; - left: 0; - width: 100%; - height: 100%; - background-color: rgba(0,0,0,0.7); -} - -.popup-content { - position: absolute; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); - background-color: #fff; - padding: 20px; - text-align: center; -} - -.close { - position: absolute; - top: 10px; - right: 10px; - font-size: 20px; - cursor: pointer; -} \ No newline at end of file diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 9b28097..2211145 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -2,7 +2,7 @@ import '../style/team_panel.css'; import {BASE} from "../Constants"; import {Team,TeamInfo,Color,User,Member} from "../model/Team/Team" -export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team }){ +export default function TeamPanel({isCoach, team,currentUserId}: {isCoach: boolean, team: Team,currentUserId:number}){ return (
@@ -13,7 +13,7 @@ export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team {isCoach && } - +
) } @@ -21,15 +21,19 @@ export default function TeamPanel({isCoach, team}: {isCoach: boolean, team: Team function TeamDisplay({ team}: {team : TeamInfo}) { return (
-
-

{team.name}

+
+

{team.name}

-

Couleur principale

- -

Couleur secondaire

- +
+

Couleur principale

+

Couleur secondaire

+
+
+ + +
) @@ -49,28 +53,31 @@ function CoachOptions ({id}:{id:number}){ ) } -function MembersDisplay({members,isCoach}:{members : Member[], isCoach : boolean}){ +function MembersDisplay({members,isCoach,idTeam,currentUserId}:{members : Member[], isCoach : boolean,idTeam : number,currentUserId:number}){ const listMember = members.map((member) => - + ); return (

Membres :

- + {isCoach && }
{listMember}
) } -function MemberDisplay({member}: {member : Member}){ +function MemberDisplay({member,isCoach,idTeam,currentUserId}: {member : Member,isCoach : boolean,idTeam:number,currentUserId:number}){ return (
Photo de profile

{member.user.name}

{member.role}

{member.user.email}

+ {isCoach && currentUserId !== member.user.id && } + {isCoach && currentUserId == member.user.id && } +
) } diff --git a/public/index.php b/public/index.php index afe7cd6..46da6c5 100644 --- a/public/index.php +++ b/public/index.php @@ -104,10 +104,9 @@ function getRoutes(): AltoRouter { $ar->map("POST", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->listTeamByName($_POST, $s))); $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamById($id,$s))); - $ar->map("GET", "/team/members/add", Action::auth(fn(SessionHandle $s) => getTeamController()->displayAddMember($s))); + $ar->map("GET", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->displayAddMember($id,$s))); $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->addMember($id,$_POST, $s))); - $ar->map("GET", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->displayDeleteMember($s))); - $ar->map("POST", "/team/members/remove", Action::auth(fn(SessionHandle $s) => getTeamController()->deleteMember($_POST, $s))); + $ar->map("POST", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam,int $idMember,SessionHandle $s) => getTeamController()->deleteMember($idTeam,$idMember, $s))); return $ar; } diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 56ac482..45b14a2 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -31,10 +31,6 @@ class TeamController { return ViewHttpResponse::twig("insert_team.html.twig", []); } - - - - /** * @param SessionHandle $session * @return ViewHttpResponse the team panel to delete a member @@ -137,7 +133,10 @@ class TeamController { 'team' => [ "info" => $result->getInfo(), "members" => $result->listMembers() - ], 'isCoach' => $role]); + ], + 'isCoach' => $role, + 'currentUserId'=>$session->getAccount()->getUser()->getId()] + ); } } @@ -145,8 +144,8 @@ class TeamController { * @param SessionHandle $session * @return ViewHttpResponse the team panel to add a member */ - public function displayAddMember(SessionHandle $session): ViewHttpResponse { - return ViewHttpResponse::twig("add_member.html.twig", []); + public function displayAddMember(int $idTeam,SessionHandle $session): ViewHttpResponse { + return ViewHttpResponse::twig("add_member.html.twig", ['idTeam'=> $idTeam]); } /** @@ -159,12 +158,21 @@ class TeamController { $errors = []; $request = HttpRequest::from($request, $errors, [ - "team" => [Validators::isInteger()], "email" => [Validators::email(), Validators::lenBetween(5, 256)], ]); - - $this->model->addMember($request['email'], $idTeam, $request['role']); - return ViewHttpResponse::redirect('/team/'.$idTeam); + if(!empty($errors)){ + return ViewHttpResponse::twig('add_member.html.twig',['badEmail' => true,'idTeam'=> $idTeam]); + } + $ret = $this->model->addMember($request['email'], $idTeam, $request['role']); + + switch($ret){ + case -1: + return ViewHttpResponse::twig('add_member.html.twig',['notFound' => true,'idTeam'=> $idTeam]); + case -2: + return ViewHttpResponse::twig('add_member.html.twig',['alreadyExisting' => true,'idTeam'=> $idTeam]); + default: + return ViewHttpResponse::redirect('/team/'.$idTeam); + } } /** @@ -173,13 +181,12 @@ class TeamController { * @param SessionHandle $session * @return HttpResponse */ - public function deleteMember(array $request, SessionHandle $session): HttpResponse { - $errors = []; - $request = HttpRequest::from($request, $errors, [ - "team" => [Validators::isInteger()], - "email" => [Validators::email(), Validators::lenBetween(5, 256)], - ]); - return $this->displayTeam($this->model->deleteMember($request['email'], intval($request['team'])), $session); + public function deleteMember(int $idTeam,int $idMember, SessionHandle $session): HttpResponse { + $ret = $this->model->deleteMember($idMember,$idTeam); + if($ret == -1 || $session->getAccount()->getUser()->getId() == $idMember ){ + return ViewHttpResponse::redirect('/'); + } + return $this->displayTeam($ret,$session); } } diff --git a/src/App/Views/add_member.html.twig b/src/App/Views/add_member.html.twig index 2cc9811..cfee16d 100644 --- a/src/App/Views/add_member.html.twig +++ b/src/App/Views/add_member.html.twig @@ -67,26 +67,43 @@ display: flex; justify-content: space-between; } + + .failed{ + color: red; + } +
+

IQBall

+

Ajouter un membre à votre équipe

- +
- - + + + {% if badEmail %} +

Email invalide

+ {% endif %} + {%if notFound %} +

Cette personne n'a pas été trouvé

+ {% endif %} + {% if alreadyExisting %} +

Cette personne est déjà dans l'équipe

+ {% endif %} +
Rôle du membre dans l'équipe :
- +
- +
diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index f14790c..9fb289a 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -94,9 +94,7 @@ class MemberGateway { "team" => [$idTeam, PDO::PARAM_INT], "user" => [$idCurrentUser, PDO::PARAM_INT] ] - )[0]['id_user'] ?? null; - return $result == null; + ); + return !empty($result); } - - } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 490da7b..2dc1162 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -41,11 +41,18 @@ class TeamModel { * @param string $mail * @param int $teamId * @param string $role - * @return void + * @return int */ - public function addMember(string $mail, int $teamId, string $role): void { - $userId = $this->users->getAccountFromMail($mail)->getUser()->getId(); - $this->members->insert($teamId, $userId, $role); + public function addMember(string $mail, int $teamId, string $role): int { + $user = $this->users->getAccountFromMail($mail); + if($user == null){ + return -1; + } + if(!$this->members->isMemberOfTeam($teamId,$user->getUser()->getId())){ + $this->members->insert($teamId, $user->getUser()->getId(), $role); + return 1; + } + return -2; } /** @@ -63,7 +70,7 @@ class TeamModel { * @return ?Team */ public function getTeam(int $idTeam, int $idCurrentUser): ?Team { - if($this->members->isMemberOfTeam($idTeam,$idCurrentUser)){ + if(!$this->members->isMemberOfTeam($idTeam,$idCurrentUser)){ return null; } $teamInfo = $this->teams->getTeamById($idTeam); @@ -77,14 +84,16 @@ class TeamModel { * @param int $teamId * @return int */ - public function deleteMember(string $mail, int $teamId): int { - $userId = $this->users->getAccountFromMail($mail)->getUser()->getId(); - $this->members->remove($teamId, $userId); + public function deleteMember(int $idMember, int $teamId): int { + $this->members->remove($teamId, $idMember); + if(empty($this->members->getMembersOfTeam($teamId))){ + $this->teams->deleteTeam($teamId); + return -1; + } return $teamId; } public function deleteTeam(string $email, int $idTeam): int{ - $this->members->isCoach($email,$idTeam); if($this->members->isCoach($email,$idTeam)){ $this->teams->deleteTeam($idTeam); return 0; -- 2.36.3 From 5aa6a7602780b68633889b2d7814f4f80434127e Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Thu, 21 Dec 2023 09:06:36 +0100 Subject: [PATCH 13/22] the bug has been fixed + set a limit for the size of team's logo --- front/style/team_panel.css | 3 ++- public/index.php | 2 +- src/App/Controller/TeamController.php | 6 +++++- 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/front/style/team_panel.css b/front/style/team_panel.css index 935ed96..8c1d435 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -77,7 +77,8 @@ header h1 a{ width: 90%; aspect-ratio: 3/2; object-fit: contain; - mix-blend-mode: color-burn; + max-width: 50%; + max-height: 50%; } #delete{ diff --git a/public/index.php b/public/index.php index 46da6c5..4a4f0d4 100644 --- a/public/index.php +++ b/public/index.php @@ -106,7 +106,7 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamById($id,$s))); $ar->map("GET", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->displayAddMember($id,$s))); $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->addMember($id,$_POST, $s))); - $ar->map("POST", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam,int $idMember,SessionHandle $s) => getTeamController()->deleteMember($idTeam,$idMember, $s))); + $ar->map("GET", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam,int $idMember,SessionHandle $s) => getTeamController()->deleteMember($idTeam,$idMember, $s))); return $ar; } diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 45b14a2..acc4839 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -156,7 +156,11 @@ class TeamController { */ public function addMember(int $idTeam,array $request, SessionHandle $session): HttpResponse { $errors = []; - + if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + return ViewHttpResponse::twig('error.html.twig', [ + 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette équipe.")], + ], HttpCodes::FORBIDDEN); + } $request = HttpRequest::from($request, $errors, [ "email" => [Validators::email(), Validators::lenBetween(5, 256)], ]); -- 2.36.3 From dcf118d12bc5d8650e50455b3f065992d5b4faf2 Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 8 Jan 2024 12:36:29 +0100 Subject: [PATCH 14/22] updated this branch comparing to the branch soutenance + added the edit of a team --- front/model/{Team => team}/Team.ts | 0 front/style/team_panel.css | 58 ++++++----- front/views/TeamPanel.tsx | 143 ++++++++++++++++++++------ public/index.php | 19 ++-- src/App/Controller/TeamController.php | 70 +++++++++++-- src/App/Views/edit_team.html.twig | 81 +++++++++++++++ src/Core/Gateway/MemberGateway.php | 2 +- src/Core/Gateway/TeamGateway.php | 34 +++++- src/Core/Model/TeamModel.php | 33 +++++- 9 files changed, 358 insertions(+), 82 deletions(-) rename front/model/{Team => team}/Team.ts (100%) create mode 100644 src/App/Views/edit_team.html.twig diff --git a/front/model/Team/Team.ts b/front/model/team/Team.ts similarity index 100% rename from front/model/Team/Team.ts rename to front/model/team/Team.ts diff --git a/front/style/team_panel.css b/front/style/team_panel.css index 8c1d435..d228d31 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -5,7 +5,7 @@ height: 100%; } -header{ +header { display: flex; justify-content: center; background-color: #525252; @@ -13,7 +13,7 @@ header{ margin-bottom: 5px; } -header h1 a{ +header h1 a { color: orange; text-decoration: none; font-size: 1.5em; @@ -22,33 +22,34 @@ header h1 a{ .square { width: 50px; height: 50px; + border: 2px white solid; } #main_color { border: solid; } -#teamInfo{ +#teamInfo { display: flex; flex-direction: column; align-items: center; width: 60%; - background-color: #8F8F8F; + background-color: #8f8f8f; padding-bottom: 10px; border-radius: 10px; } -#firstPart{ +#firstPart { display: flex; flex-direction: column; align-items: center; } -#teamName{ +#teamName { font-size: 2.8em; } -#colors{ +#colors { display: flex; flex-direction: column; } @@ -57,7 +58,7 @@ header h1 a{ justify-content: space-between; } -#colorsTitle{ +#colorsTitle { width: 110%; display: flex; flex-direction: row; @@ -66,54 +67,61 @@ header h1 a{ color: white; } - -#actualColors{ +#actualColors { display: flex; flex-direction: row; justify-content: space-around; } #logo { - width: 90%; aspect-ratio: 3/2; object-fit: contain; - max-width: 50%; - max-height: 50%; + max-width: 70%; + max-height: 70%; } -#delete{ - border-radius:10px ; +#delete { + border-radius: 10px; background-color: red; color: white; margin-top: 10px; margin-bottom: 10px; + margin-right: 5px; } -#headMembers{ +#edit{ + border-radius: 10px; + background-color: orange; + color: white; + margin-top: 10px; + margin-bottom: 10px; +} + +#headMembers { width: 33%; display: flex; flex-direction: row; justify-content: space-evenly; } -#addMember{ +#addMember { height: 30px; aspect-ratio: 1/1; border-radius: 100%; align-self: center; } -#Members{ +#Members { display: flex; flex-direction: column; - background-color: #BCBCBC; + background-color: #bcbcbc; width: 60%; align-items: center; justify-content: space-around; border-radius: 10px; } -.Member{ +.Member { width: 60%; background-color: white; display: flex; @@ -123,11 +131,9 @@ header h1 a{ border-radius: 10px; margin-top: 5px; margin-bottom: 5px; - -} - -#profilePicture{ - height:40px; - width:40px; } +#profilePicture { + height: 40px; + width: 40px; +} \ No newline at end of file diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 2211145..fc77915 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -1,24 +1,38 @@ -import '../style/team_panel.css'; -import {BASE} from "../Constants"; -import {Team,TeamInfo,Color,User,Member} from "../model/Team/Team" +import "../style/team_panel.css" +import { BASE } from "../Constants" +import { Team, TeamInfo, Color, User, Member } from "../model/team/Team" -export default function TeamPanel({isCoach, team,currentUserId}: {isCoach: boolean, team: Team,currentUserId:number}){ +export default function TeamPanel({ + isCoach, + team, + currentUserId, + }: { + isCoach: boolean + team: Team + currentUserId: number +}) { return (
-

IQBall

+

+ IQBall +

- + - {isCoach && } + {isCoach && } - - +
) } -function TeamDisplay({ team}: {team : TeamInfo}) { +function TeamDisplay({ team }: { team: TeamInfo }) { return (
@@ -31,53 +45,124 @@ function TeamDisplay({ team}: {team : TeamInfo}) {

Couleur secondaire

- - + +
) } -function ColorDisplay({color}: {color : Color}){ - return( -
- ) +function ColorDisplay({ color }: { color: Color }) { + return
} -function CoachOptions ({id}:{id:number}){ +function CoachOptions({ id }: { id: number }) { return (
- + +
) } -function MembersDisplay({members,isCoach,idTeam,currentUserId}:{members : Member[], isCoach : boolean,idTeam : number,currentUserId:number}){ - const listMember = members.map((member) => - - ); +function MembersDisplay({ + members, + isCoach, + idTeam, + currentUserId, + }: { + members: Member[] + isCoach: boolean + idTeam: number + currentUserId: number +}) { + const listMember = members.map((member) => ( + + )) return (

Membres :

- {isCoach && } + {isCoach && ( + + )}
{listMember}
) } -function MemberDisplay({member,isCoach,idTeam,currentUserId}: {member : Member,isCoach : boolean,idTeam:number,currentUserId:number}){ +function MemberDisplay({ + member, + isCoach, + idTeam, + currentUserId, + }: { + member: Member + isCoach: boolean + idTeam: number + currentUserId: number +}) { return (
- Photo de profile + Photo de profile

{member.user.name}

{member.role}

{member.user.email}

- {isCoach && currentUserId !== member.user.id && } - {isCoach && currentUserId == member.user.id && } - + {isCoach && currentUserId !== member.user.id && ( + + )} + {isCoach && currentUserId == member.user.id && ( + + )}
) -} +} \ No newline at end of file diff --git a/public/index.php b/public/index.php index 4a4f0d4..113e79d 100644 --- a/public/index.php +++ b/public/index.php @@ -1,6 +1,5 @@ map("GET", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->displayListTeamByName($s))); $ar->map("POST", "/team/search", Action::auth(fn(SessionHandle $s) => getTeamController()->listTeamByName($_POST, $s))); $ar->map("GET", "/team/[i:id]", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayTeam($id, $s))); - $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->deleteTeamById($id,$s))); - $ar->map("GET", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->displayAddMember($id,$s))); - $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id,SessionHandle $s) => getTeamController()->addMember($id,$_POST, $s))); - $ar->map("GET", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam,int $idMember,SessionHandle $s) => getTeamController()->deleteMember($idTeam,$idMember, $s))); + $ar->map("GET", "/team/[i:id]/delete", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->deleteTeamById($id, $s))); + $ar->map("GET", "/team/[i:id]/addMember", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayAddMember($id, $s))); + $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->addMember($id, $_POST, $s))); + $ar->map("GET", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam, int $idMember, SessionHandle $s) => getTeamController()->deleteMember($idTeam, $idMember, $s))); + $ar->map("GET", "/team/[i:id]/edit", Action::auth(fn(int $idTeam,SessionHandle $s) => getTeamController()->displayEditTeam($idTeam,$s))); + $ar->map("POST", "/team/[i:id]/edit", Action::auth(fn(int $idTeam,SessionHandle $s) => getTeamController()->editTeam($idTeam,$_POST,$s))); + return $ar; } @@ -119,11 +121,10 @@ function runMatch($match, MutableSessionHandle $session): HttpResponse { ], HttpCodes::NOT_FOUND); } - return App::runAction($basePath . '/login', $match['target'], $match['params'], $session); + return App::runAction('/login', $match['target'], $match['params'], $session); } - //this is a global variable $basePath = get_public_path(__DIR__); -App::render(runMatch(getRoutes()->match(), PhpSessionHandle::init()), fn() => getTwig()); +App::render(runMatch(getRoutes()->match(), PhpSessionHandle::init()), fn() => getTwig()); \ No newline at end of file diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index acc4839..92ecc14 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -64,7 +64,7 @@ class TeamController { } $teamId = $this->model->createTeam($request['name'], $request['picture'], $request['main_color'], $request['second_color']); $this->model->addMember($session->getAccount()->getUser()->getEmail(),$teamId,'COACH'); - return ViewHttpResponse::redirect('/team/'.$teamId); + return HttpResponse::redirect('/team/'.$teamId); } /** @@ -101,6 +101,7 @@ class TeamController { } /** + * Delete a team with its id * @param int $id * @param SessionHandle $session * @return HttpResponse @@ -111,10 +112,11 @@ class TeamController { if($ret != 0){ return ViewHttpResponse::twig('display_team.html.twig',['notDeleted' => true]); } - return ViewHttpResponse::redirect('/'); + return HttpResponse::redirect('/'); } /** + * Display a team with its id * @param int $id * @param SessionHandle $session * @return ViewHttpResponse a view that displays given team information @@ -141,6 +143,7 @@ class TeamController { } /** + * @param int $idTeam * @param SessionHandle $session * @return ViewHttpResponse the team panel to add a member */ @@ -150,6 +153,7 @@ class TeamController { /** * add a member to a team + * @param int $idTeam * @param array $request * @param SessionHandle $session * @return HttpResponse @@ -158,7 +162,7 @@ class TeamController { $errors = []; if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ return ViewHttpResponse::twig('error.html.twig', [ - 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette équipe.")], + 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], ], HttpCodes::FORBIDDEN); } $request = HttpRequest::from($request, $errors, [ @@ -175,22 +179,68 @@ class TeamController { case -2: return ViewHttpResponse::twig('add_member.html.twig',['alreadyExisting' => true,'idTeam'=> $idTeam]); default: - return ViewHttpResponse::redirect('/team/'.$idTeam); + return HttpResponse::redirect('/team/'.$idTeam); } } /** - * remove a member from a team - * @param array $request + * remove a member from a team with their ids + * @param int $idTeam + * @param int $idMember * @param SessionHandle $session * @return HttpResponse */ public function deleteMember(int $idTeam,int $idMember, SessionHandle $session): HttpResponse { - $ret = $this->model->deleteMember($idMember,$idTeam); - if($ret == -1 || $session->getAccount()->getUser()->getId() == $idMember ){ - return ViewHttpResponse::redirect('/'); + if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + return ViewHttpResponse::twig('error.html.twig', [ + 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], + ], HttpCodes::FORBIDDEN); } - return $this->displayTeam($ret,$session); + $teamId = $this->model->deleteMember($idMember,$idTeam); + if($teamId == -1 || $session->getAccount()->getUser()->getId() == $idMember ){ + return HttpResponse::redirect('/'); + } + return $this->displayTeam($teamId,$session); + } + + /** + * @param int $idTeam + * @param SessionHandle $session + * @return ViewHttpResponse + */ + public function displayEditTeam(int $idTeam,SessionHandle $session): ViewHttpResponse { + return ViewHttpResponse::twig("edit_team.html.twig", ['team' => $this->model->getTeam($idTeam,$session->getAccount()->getUser()->getId())]); } + /** + * @param int $idTeam + * @param array $request + * @param SessionHandle $session + * @return HttpResponse + */ + public function editTeam(int $idTeam,array $request,SessionHandle $session): HttpResponse{ + if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + return ViewHttpResponse::twig('error.html.twig', [ + 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], + ], HttpCodes::FORBIDDEN); + } + $failures = []; + $request = HttpRequest::from($request, $failures, [ + "name" => [Validators::lenBetween(1, 32), Validators::nameWithSpaces()], + "main_color" => [Validators::hexColor()], + "second_color" => [Validators::hexColor()], + "picture" => [Validators::isURL()], + ]); + if (!empty($failures)) { + $badFields = []; + foreach ($failures as $e) { + if ($e instanceof FieldValidationFail) { + $badFields[] = $e->getFieldName(); + } + } + return ViewHttpResponse::twig('edit_team.html.twig', ['bad_fields' => $badFields]); + } + $this->model->editTeam($idTeam,$request['name'], $request['picture'], $request['main_color'], $request['second_color']); + return HttpResponse::redirect('/team/'.$idTeam); + } } diff --git a/src/App/Views/edit_team.html.twig b/src/App/Views/edit_team.html.twig new file mode 100644 index 0000000..00eef84 --- /dev/null +++ b/src/App/Views/edit_team.html.twig @@ -0,0 +1,81 @@ + + + + + Insertion view + + + + +
+

Modifier votre équipe

+ +
+ + + + + + + + +
+
+ +
+ +
+ + + \ No newline at end of file diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index 9fb289a..aeb2042 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -41,7 +41,7 @@ class MemberGateway { */ public function getMembersOfTeam(int $teamId): array { $rows = $this->con->fetch( - "SELECT a.id,a.email,a.username,a.profilePicture,m.role FROM Account a,Team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", + "SELECT a.id,a.email,a.username,a.profilePicture,m.role FROM Account a,team t,Member m WHERE t.id = :id AND m.id_team = t.id AND m.id_user = a.id", [ ":id" => [$teamId, PDO::PARAM_INT], ] diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 0160e00..601fe25 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -23,7 +23,7 @@ class TeamGateway { */ public function insert(string $name, string $picture, string $mainColor, string $secondColor): int { $this->con->exec( - "INSERT INTO Team(name, picture, main_color, second_color) VALUES (:team_name , :picture, :main_color, :second_color)", + "INSERT INTO team(name, picture, main_color, second_color) VALUES (:team_name , :picture, :main_color, :second_color)", [ ":team_name" => [$name, PDO::PARAM_STR], ":picture" => [$picture, PDO::PARAM_STR], @@ -41,7 +41,7 @@ class TeamGateway { */ public function listByName(string $name,int $id): array { $result = $this->con->fetch( - "SELECT t.* FROM Team t, Member m WHERE t.name LIKE '%' || :name || '%' AND t.id=m.id_team AND m.id_user=:id", + "SELECT t.* FROM team t, Member m WHERE t.name LIKE '%' || :name || '%' AND t.id=m.id_team AND m.id_user=:id", [ ":name" => [$name, PDO::PARAM_STR], "id" => [$id, PDO::PARAM_INT] @@ -56,7 +56,7 @@ class TeamGateway { */ public function getTeamById(int $id): ?TeamInfo { $row = $this->con->fetch( - "SELECT * FROM Team WHERE id = :id", + "SELECT * FROM team WHERE id = :id", [ ":id" => [$id, PDO::PARAM_INT], ] @@ -73,7 +73,7 @@ class TeamGateway { */ public function getTeamIdByName(string $name): ?int { return $this->con->fetch( - "SELECT id FROM Team WHERE name = :name", + "SELECT id FROM team WHERE name = :name", [ ":name" => [$name, PDO::PARAM_INT], ] @@ -98,4 +98,30 @@ class TeamGateway { ); } + /** + * @param int $idTeam + * @param string $newName + * @param string $newPicture + * @param string $newMainColor + * @param string $newSecondColor + * @return void + */ + public function editTeam(int $idTeam,string $newName,string $newPicture, string $newMainColor, string $newSecondColor){ + $this->con->exec( + "UPDATE team + SET name = :newName, + picture = :newPicture, + main_color = :newMainColor, + second_color = :newSecondColor + WHERE id = :team", + [ + "team" => [$idTeam, PDO::PARAM_INT], + "newName" => [$newName, PDO::PARAM_STR], + "newPicture" => [$newPicture, PDO::PARAM_STR], + "newMainColor" => [$newMainColor, PDO::PARAM_STR], + "newSecondColor" => [$newSecondColor, PDO::PARAM_STR], + ] + ); + } + } diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 2dc1162..6bdd615 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -26,6 +26,7 @@ class TeamModel { } /** + * Create a team * @param string $name * @param string $picture * @param string $mainColor @@ -37,7 +38,7 @@ class TeamModel { } /** - * adds a member to a team + * add a member to a team * @param string $mail * @param int $teamId * @param string $role @@ -67,7 +68,7 @@ class TeamModel { /** * @param int $idTeam * @param int $idCurrentUser - * @return ?Team + * @return Team|null */ public function getTeam(int $idTeam, int $idCurrentUser): ?Team { if(!$this->members->isMemberOfTeam($idTeam,$idCurrentUser)){ @@ -80,7 +81,7 @@ class TeamModel { /** * delete a member from given team identifier - * @param string $mail + * @param int $idMember * @param int $teamId * @return int */ @@ -93,6 +94,12 @@ class TeamModel { return $teamId; } + /** + * Delete a team + * @param string $email + * @param int $idTeam + * @return int + */ public function deleteTeam(string $email, int $idTeam): int{ if($this->members->isCoach($email,$idTeam)){ $this->teams->deleteTeam($idTeam); @@ -101,7 +108,27 @@ class TeamModel { return -1; } + /** + * Verify if the account associated to an email is in a specific team indicated with its id + * @param int $idTeam + * @param string $email + * @return bool + */ public function isCoach(int $idTeam, string $email): bool{ return $this->members->isCoach($email,$idTeam); } + + /** + * Edit a team with its id, and replace the current attributes with the new ones + * @param int $idTeam + * @param string $newName + * @param string $newPicture + * @param string $newMainColor + * @param string $newSecondColor + * @return void + */ + public function editTeam(int $idTeam,string $newName,string $newPicture, string $newMainColor, string $newSecondColor){ + $this->teams->editTeam($idTeam,$newName,$newPicture, $newMainColor, $newSecondColor); + } + } -- 2.36.3 From fafe4a1ff4c178df0c3be09a163e4a8caf67ca7b Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 8 Jan 2024 12:50:06 +0100 Subject: [PATCH 15/22] format and verified --- front/model/team/Team.ts | 10 +-- front/style/team_panel.css | 4 +- front/views/Editor.tsx | 1 - front/views/TeamPanel.tsx | 30 ++++----- public/index.php | 6 +- src/Api/Controller/APITacticController.php | 2 +- src/App/Controller/TeamController.php | 75 +++++++++++----------- src/Core/Data/Account.php | 1 - src/Core/Data/Member.php | 1 - src/Core/Data/User.php | 3 +- src/Core/Gateway/AccountGateway.php | 8 +-- src/Core/Gateway/MemberGateway.php | 18 +++--- src/Core/Gateway/TeamGateway.php | 22 +++---- src/Core/Model/AuthModel.php | 6 +- src/Core/Model/TeamModel.php | 28 ++++---- 15 files changed, 106 insertions(+), 109 deletions(-) diff --git a/front/model/team/Team.ts b/front/model/team/Team.ts index 99fe6dd..3a7f983 100644 --- a/front/model/team/Team.ts +++ b/front/model/team/Team.ts @@ -1,4 +1,4 @@ -export interface TeamInfo{ +export interface TeamInfo { id: number name: string picture: string @@ -6,7 +6,7 @@ export interface TeamInfo{ secondColor: Color } -export interface Color{ +export interface Color { hex: string } @@ -15,14 +15,14 @@ export interface Team { members: Member[] } -export interface Member{ +export interface Member { user: User role: string } -export interface User{ +export interface User { id: number name: string email: string profilePicture: string -} \ No newline at end of file +} diff --git a/front/style/team_panel.css b/front/style/team_panel.css index d228d31..bb573ff 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -89,7 +89,7 @@ header h1 a { margin-right: 5px; } -#edit{ +#edit { border-radius: 10px; background-color: orange; color: white; @@ -136,4 +136,4 @@ header h1 a { #profilePicture { height: 40px; width: 40px; -} \ No newline at end of file +} diff --git a/front/views/Editor.tsx b/front/views/Editor.tsx index 5adbe51..084dc06 100644 --- a/front/views/Editor.tsx +++ b/front/views/Editor.tsx @@ -198,7 +198,6 @@ function EditorView({
-
diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index fc77915..66826b0 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -3,10 +3,10 @@ import { BASE } from "../Constants" import { Team, TeamInfo, Color, User, Member } from "../model/team/Team" export default function TeamPanel({ - isCoach, - team, - currentUserId, - }: { + isCoach, + team, + currentUserId, +}: { isCoach: boolean team: Team currentUserId: number @@ -81,11 +81,11 @@ function CoachOptions({ id }: { id: number }) { } function MembersDisplay({ - members, - isCoach, - idTeam, - currentUserId, - }: { + members, + isCoach, + idTeam, + currentUserId, +}: { members: Member[] isCoach: boolean idTeam: number @@ -119,11 +119,11 @@ function MembersDisplay({ } function MemberDisplay({ - member, - isCoach, - idTeam, - currentUserId, - }: { + member, + isCoach, + idTeam, + currentUserId, +}: { member: Member isCoach: boolean idTeam: number @@ -165,4 +165,4 @@ function MemberDisplay({ )}
) -} \ No newline at end of file +} diff --git a/public/index.php b/public/index.php index 113e79d..3d49a14 100644 --- a/public/index.php +++ b/public/index.php @@ -106,8 +106,8 @@ function getRoutes(): AltoRouter { $ar->map("GET", "/team/[i:id]/addMember", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->displayAddMember($id, $s))); $ar->map("POST", "/team/[i:id]/addMember", Action::auth(fn(int $id, SessionHandle $s) => getTeamController()->addMember($id, $_POST, $s))); $ar->map("GET", "/team/[i:idTeam]/remove/[i:idMember]", Action::auth(fn(int $idTeam, int $idMember, SessionHandle $s) => getTeamController()->deleteMember($idTeam, $idMember, $s))); - $ar->map("GET", "/team/[i:id]/edit", Action::auth(fn(int $idTeam,SessionHandle $s) => getTeamController()->displayEditTeam($idTeam,$s))); - $ar->map("POST", "/team/[i:id]/edit", Action::auth(fn(int $idTeam,SessionHandle $s) => getTeamController()->editTeam($idTeam,$_POST,$s))); + $ar->map("GET", "/team/[i:id]/edit", Action::auth(fn(int $idTeam, SessionHandle $s) => getTeamController()->displayEditTeam($idTeam, $s))); + $ar->map("POST", "/team/[i:id]/edit", Action::auth(fn(int $idTeam, SessionHandle $s) => getTeamController()->editTeam($idTeam, $_POST, $s))); return $ar; @@ -127,4 +127,4 @@ function runMatch($match, MutableSessionHandle $session): HttpResponse { //this is a global variable $basePath = get_public_path(__DIR__); -App::render(runMatch(getRoutes()->match(), PhpSessionHandle::init()), fn() => getTwig()); \ No newline at end of file +App::render(runMatch(getRoutes()->match(), PhpSessionHandle::init()), fn() => getTwig()); diff --git a/src/Api/Controller/APITacticController.php b/src/Api/Controller/APITacticController.php index 79e766c..a116add 100644 --- a/src/Api/Controller/APITacticController.php +++ b/src/Api/Controller/APITacticController.php @@ -36,7 +36,7 @@ class APITacticController { "name" => [Validators::lenBetween(1, 50), Validators::nameWithSpaces()], ], function (HttpRequest $request) use ($tactic_id, $account) { - $failures = $this->model->updateName($tactic_id, $request["name"], $account->getId()); + $failures = $this->model->updateName($tactic_id, $request["name"], $account->getUser()->getId()); if (!empty($failures)) { //TODO find a system to handle Unauthorized error codes more easily from failures. diff --git a/src/App/Controller/TeamController.php b/src/App/Controller/TeamController.php index 92ecc14..fc78234 100644 --- a/src/App/Controller/TeamController.php +++ b/src/App/Controller/TeamController.php @@ -63,8 +63,8 @@ class TeamController { return ViewHttpResponse::twig('insert_team.html.twig', ['bad_fields' => $badFields]); } $teamId = $this->model->createTeam($request['name'], $request['picture'], $request['main_color'], $request['second_color']); - $this->model->addMember($session->getAccount()->getUser()->getEmail(),$teamId,'COACH'); - return HttpResponse::redirect('/team/'.$teamId); + $this->model->addMember($session->getAccount()->getUser()->getEmail(), $teamId, 'COACH'); + return HttpResponse::redirect('/team/' . $teamId); } /** @@ -92,7 +92,7 @@ class TeamController { return ViewHttpResponse::twig('list_team_by_name.html.twig', ['bad_field' => $badField]); } - $teams = $this->model->listByName($request['name'],$session->getAccount()->getUser()->getId()); + $teams = $this->model->listByName($request['name'], $session->getAccount()->getUser()->getId()); if (empty($teams)) { return ViewHttpResponse::twig('display_teams.html.twig', []); @@ -106,11 +106,11 @@ class TeamController { * @param SessionHandle $session * @return HttpResponse */ - public function deleteTeamById(int $id, SessionHandle $session):HttpResponse{ + public function deleteTeamById(int $id, SessionHandle $session): HttpResponse { $a = $session->getAccount(); - $ret = $this->model->deleteTeam($a->getUser()->getEmail(),$id); - if($ret != 0){ - return ViewHttpResponse::twig('display_team.html.twig',['notDeleted' => true]); + $ret = $this->model->deleteTeam($a->getUser()->getEmail(), $id); + if($ret != 0) { + return ViewHttpResponse::twig('display_team.html.twig', ['notDeleted' => true]); } return HttpResponse::redirect('/'); } @@ -122,22 +122,23 @@ class TeamController { * @return ViewHttpResponse a view that displays given team information */ public function displayTeam(int $id, SessionHandle $session): ViewHttpResponse { - $result = $this->model->getTeam($id,$session->getAccount()->getUser()->getId()); - if($result == null){ + $result = $this->model->getTeam($id, $session->getAccount()->getUser()->getId()); + if($result == null) { return ViewHttpResponse::twig('error.html.twig', [ 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette équipe.")], ], HttpCodes::FORBIDDEN); - } - else{ - $role = $this->model->isCoach($id,$session->getAccount()->getUser()->getEmail()); + } else { + $role = $this->model->isCoach($id, $session->getAccount()->getUser()->getEmail()); - return ViewHttpResponse::react('views/TeamPanel.tsx', [ + return ViewHttpResponse::react( + 'views/TeamPanel.tsx', + [ 'team' => [ "info" => $result->getInfo(), - "members" => $result->listMembers() + "members" => $result->listMembers(), ], 'isCoach' => $role, - 'currentUserId'=>$session->getAccount()->getUser()->getId()] + 'currentUserId' => $session->getAccount()->getUser()->getId()] ); } } @@ -147,8 +148,8 @@ class TeamController { * @param SessionHandle $session * @return ViewHttpResponse the team panel to add a member */ - public function displayAddMember(int $idTeam,SessionHandle $session): ViewHttpResponse { - return ViewHttpResponse::twig("add_member.html.twig", ['idTeam'=> $idTeam]); + public function displayAddMember(int $idTeam, SessionHandle $session): ViewHttpResponse { + return ViewHttpResponse::twig("add_member.html.twig", ['idTeam' => $idTeam]); } /** @@ -158,9 +159,9 @@ class TeamController { * @param SessionHandle $session * @return HttpResponse */ - public function addMember(int $idTeam,array $request, SessionHandle $session): HttpResponse { + public function addMember(int $idTeam, array $request, SessionHandle $session): HttpResponse { $errors = []; - if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + if(!$this->model->isCoach($idTeam, $session->getAccount()->getUser()->getEmail())) { return ViewHttpResponse::twig('error.html.twig', [ 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], ], HttpCodes::FORBIDDEN); @@ -168,18 +169,18 @@ class TeamController { $request = HttpRequest::from($request, $errors, [ "email" => [Validators::email(), Validators::lenBetween(5, 256)], ]); - if(!empty($errors)){ - return ViewHttpResponse::twig('add_member.html.twig',['badEmail' => true,'idTeam'=> $idTeam]); + if(!empty($errors)) { + return ViewHttpResponse::twig('add_member.html.twig', ['badEmail' => true,'idTeam' => $idTeam]); } $ret = $this->model->addMember($request['email'], $idTeam, $request['role']); - switch($ret){ + switch($ret) { case -1: - return ViewHttpResponse::twig('add_member.html.twig',['notFound' => true,'idTeam'=> $idTeam]); + return ViewHttpResponse::twig('add_member.html.twig', ['notFound' => true,'idTeam' => $idTeam]); case -2: - return ViewHttpResponse::twig('add_member.html.twig',['alreadyExisting' => true,'idTeam'=> $idTeam]); + return ViewHttpResponse::twig('add_member.html.twig', ['alreadyExisting' => true,'idTeam' => $idTeam]); default: - return HttpResponse::redirect('/team/'.$idTeam); + return HttpResponse::redirect('/team/' . $idTeam); } } @@ -190,17 +191,17 @@ class TeamController { * @param SessionHandle $session * @return HttpResponse */ - public function deleteMember(int $idTeam,int $idMember, SessionHandle $session): HttpResponse { - if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + public function deleteMember(int $idTeam, int $idMember, SessionHandle $session): HttpResponse { + if(!$this->model->isCoach($idTeam, $session->getAccount()->getUser()->getEmail())) { return ViewHttpResponse::twig('error.html.twig', [ 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], ], HttpCodes::FORBIDDEN); } - $teamId = $this->model->deleteMember($idMember,$idTeam); - if($teamId == -1 || $session->getAccount()->getUser()->getId() == $idMember ){ + $teamId = $this->model->deleteMember($idMember, $idTeam); + if($teamId == -1 || $session->getAccount()->getUser()->getId() == $idMember) { return HttpResponse::redirect('/'); } - return $this->displayTeam($teamId,$session); + return $this->displayTeam($teamId, $session); } /** @@ -208,18 +209,18 @@ class TeamController { * @param SessionHandle $session * @return ViewHttpResponse */ - public function displayEditTeam(int $idTeam,SessionHandle $session): ViewHttpResponse { - return ViewHttpResponse::twig("edit_team.html.twig", ['team' => $this->model->getTeam($idTeam,$session->getAccount()->getUser()->getId())]); + public function displayEditTeam(int $idTeam, SessionHandle $session): ViewHttpResponse { + return ViewHttpResponse::twig("edit_team.html.twig", ['team' => $this->model->getTeam($idTeam, $session->getAccount()->getUser()->getId())]); } /** * @param int $idTeam - * @param array $request + * @param array $request * @param SessionHandle $session * @return HttpResponse */ - public function editTeam(int $idTeam,array $request,SessionHandle $session): HttpResponse{ - if(!$this->model->isCoach($idTeam,$session->getAccount()->getUser()->getEmail())){ + public function editTeam(int $idTeam, array $request, SessionHandle $session): HttpResponse { + if(!$this->model->isCoach($idTeam, $session->getAccount()->getUser()->getEmail())) { return ViewHttpResponse::twig('error.html.twig', [ 'failures' => [ValidationFail::unauthorized("Vous n'avez pas accès à cette action pour cette équipe.")], ], HttpCodes::FORBIDDEN); @@ -240,7 +241,7 @@ class TeamController { } return ViewHttpResponse::twig('edit_team.html.twig', ['bad_fields' => $badFields]); } - $this->model->editTeam($idTeam,$request['name'], $request['picture'], $request['main_color'], $request['second_color']); - return HttpResponse::redirect('/team/'.$idTeam); + $this->model->editTeam($idTeam, $request['name'], $request['picture'], $request['main_color'], $request['second_color']); + return HttpResponse::redirect('/team/' . $idTeam); } } diff --git a/src/Core/Data/Account.php b/src/Core/Data/Account.php index 01be656..01f5406 100755 --- a/src/Core/Data/Account.php +++ b/src/Core/Data/Account.php @@ -8,7 +8,6 @@ namespace IQBall\Core\Data; * to share to other users, or non-needed public information */ class Account { - /** * @var string string token */ diff --git a/src/Core/Data/Member.php b/src/Core/Data/Member.php index 37f8f04..30e4202 100755 --- a/src/Core/Data/Member.php +++ b/src/Core/Data/Member.php @@ -6,7 +6,6 @@ namespace IQBall\Core\Data; * information about a team member */ class Member implements \JsonSerializable { - private User $user; /** diff --git a/src/Core/Data/User.php b/src/Core/Data/User.php index b1fdd22..71e0dd1 100644 --- a/src/Core/Data/User.php +++ b/src/Core/Data/User.php @@ -5,7 +5,6 @@ namespace IQBall\Core\Data; use _PHPStan_4c4f22f13\Nette\Utils\Json; class User implements \JsonSerializable { - /** * @var string $email user's mail address */ @@ -70,4 +69,4 @@ class User implements \JsonSerializable { public function jsonSerialize() { return get_object_vars($this); } -} \ No newline at end of file +} diff --git a/src/Core/Gateway/AccountGateway.php b/src/Core/Gateway/AccountGateway.php index 1d109d0..a9c3e18 100644 --- a/src/Core/Gateway/AccountGateway.php +++ b/src/Core/Gateway/AccountGateway.php @@ -17,13 +17,13 @@ class AccountGateway { $this->con = $con; } - public function insertAccount(string $name, string $email, string $token, string $hash,string $profilePicture): int { + public function insertAccount(string $name, string $email, string $token, string $hash, string $profilePicture): int { $this->con->exec("INSERT INTO Account(username, hash, email, token,profilePicture) VALUES (:username,:hash,:email,:token,:profilePic)", [ ':username' => [$name, PDO::PARAM_STR], ':hash' => [$hash, PDO::PARAM_STR], ':email' => [$email, PDO::PARAM_STR], ':token' => [$token, PDO::PARAM_STR], - ':profilePic' => [$profilePicture, PDO::PARAM_STR] + ':profilePic' => [$profilePicture, PDO::PARAM_STR], ]); return intval($this->con->lastInsertId()); } @@ -66,7 +66,7 @@ class AccountGateway { return null; } - return new Account($acc["token"],new User($email,$acc["username"],$acc["id"],$acc["profilePicture"])); + return new Account($acc["token"], new User($email, $acc["username"], $acc["id"], $acc["profilePicture"])); } /** @@ -79,7 +79,7 @@ class AccountGateway { return null; } - return new Account($acc["token"],new User($acc["email"],$acc["username"],$acc["id"],$acc["profilePicture"])); + return new Account($acc["token"], new User($acc["email"], $acc["username"], $acc["id"], $acc["profilePicture"])); } diff --git a/src/Core/Gateway/MemberGateway.php b/src/Core/Gateway/MemberGateway.php index aeb2042..a5116e8 100644 --- a/src/Core/Gateway/MemberGateway.php +++ b/src/Core/Gateway/MemberGateway.php @@ -46,7 +46,7 @@ class MemberGateway { ":id" => [$teamId, PDO::PARAM_INT], ] ); - return array_map(fn($row) => new Member(new User($row['email'],$row['username'],$row['id'],$row['profilePicture']), $teamId, $row['role']),$rows); + return array_map(fn($row) => new Member(new User($row['email'], $row['username'], $row['id'], $row['profilePicture']), $teamId, $row['role']), $rows); } /** @@ -72,12 +72,12 @@ class MemberGateway { */ public function isCoach(string $email, int $idTeam): bool { $result = $this->con->fetch( - "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", - [ + "SELECT role FROM Member WHERE id_team=:team AND id_user = (SELECT id FROM Account WHERE email=:email)", + [ "team" => [$idTeam, PDO::PARAM_INT], - "email" => [$email, PDO::PARAM_STR] + "email" => [$email, PDO::PARAM_STR], ] - )[0]['role']; + )[0]['role']; return $result == 'COACH'; } @@ -87,14 +87,14 @@ class MemberGateway { * @param int $idCurrentUser * @return bool */ - public function isMemberOfTeam(int $idTeam,int $idCurrentUser): bool { + public function isMemberOfTeam(int $idTeam, int $idCurrentUser): bool { $result = $this->con->fetch( "SELECT id_user FROM Member WHERE id_team = :team AND id_user = :user", - [ + [ "team" => [$idTeam, PDO::PARAM_INT], - "user" => [$idCurrentUser, PDO::PARAM_INT] + "user" => [$idCurrentUser, PDO::PARAM_INT], ] - ); + ); return !empty($result); } } diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 601fe25..9804e6b 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -39,12 +39,12 @@ class TeamGateway { * @param int $id * @return TeamInfo[] */ - public function listByName(string $name,int $id): array { + public function listByName(string $name, int $id): array { $result = $this->con->fetch( "SELECT t.* FROM team t, Member m WHERE t.name LIKE '%' || :name || '%' AND t.id=m.id_team AND m.id_user=:id", [ ":name" => [$name, PDO::PARAM_STR], - "id" => [$id, PDO::PARAM_INT] + "id" => [$id, PDO::PARAM_INT], ] ); return array_map(fn($row) => new TeamInfo($row['id'], $row['name'], $row['picture'], Color::from($row['main_color']), Color::from($row['second_color'])), $result); @@ -56,11 +56,11 @@ class TeamGateway { */ public function getTeamById(int $id): ?TeamInfo { $row = $this->con->fetch( - "SELECT * FROM team WHERE id = :id", - [ + "SELECT * FROM team WHERE id = :id", + [ ":id" => [$id, PDO::PARAM_INT], ] - )[0] ?? null; + )[0] ?? null; if ($row == null) { return null; } @@ -73,11 +73,11 @@ class TeamGateway { */ public function getTeamIdByName(string $name): ?int { return $this->con->fetch( - "SELECT id FROM team WHERE name = :name", - [ + "SELECT id FROM team WHERE name = :name", + [ ":name" => [$name, PDO::PARAM_INT], ] - )[0]['id'] ?? null; + )[0]['id'] ?? null; } /** @@ -87,13 +87,13 @@ class TeamGateway { $this->con->exec( "DELETE FROM Member WHERE id_team=:team", [ - "team" => [$idTeam, PDO::PARAM_INT] + "team" => [$idTeam, PDO::PARAM_INT], ] ); $this->con->exec( "DELETE FROM TEAM WHERE id=:team", [ - "team" => [$idTeam, PDO::PARAM_INT] + "team" => [$idTeam, PDO::PARAM_INT], ] ); } @@ -106,7 +106,7 @@ class TeamGateway { * @param string $newSecondColor * @return void */ - public function editTeam(int $idTeam,string $newName,string $newPicture, string $newMainColor, string $newSecondColor){ + public function editTeam(int $idTeam, string $newName, string $newPicture, string $newMainColor, string $newSecondColor) { $this->con->exec( "UPDATE team SET name = :newName, diff --git a/src/Core/Model/AuthModel.php b/src/Core/Model/AuthModel.php index dcf1a66..bc29248 100644 --- a/src/Core/Model/AuthModel.php +++ b/src/Core/Model/AuthModel.php @@ -46,8 +46,8 @@ class AuthModel { $hash = password_hash($password, PASSWORD_DEFAULT); $token = $this->generateToken(); - $accountId = $this->gateway->insertAccount($username, $email, $token, $hash,self::DEFAULT_PROFILE_PICTURE); - return new Account($token,new User($email,$username,$accountId,self::DEFAULT_PROFILE_PICTURE)); + $accountId = $this->gateway->insertAccount($username, $email, $token, $hash, self::DEFAULT_PROFILE_PICTURE); + return new Account($token, new User($email, $username, $accountId, self::DEFAULT_PROFILE_PICTURE)); } /** @@ -68,7 +68,7 @@ class AuthModel { public function login(string $email, string $password, array &$failures): ?Account { $hash = $this->gateway->getHash($email); if ($hash == null or (!password_verify($password, $hash))) { - $failures[] = new ValidationFail("email","Adresse email ou mot de passe invalide"); + $failures[] = new ValidationFail("email", "Adresse email ou mot de passe invalide"); return null; } return $this->gateway->getAccountFromMail($email); diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 6bdd615..9e2821a 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -46,10 +46,10 @@ class TeamModel { */ public function addMember(string $mail, int $teamId, string $role): int { $user = $this->users->getAccountFromMail($mail); - if($user == null){ + if($user == null) { return -1; } - if(!$this->members->isMemberOfTeam($teamId,$user->getUser()->getId())){ + if(!$this->members->isMemberOfTeam($teamId, $user->getUser()->getId())) { $this->members->insert($teamId, $user->getUser()->getId(), $role); return 1; } @@ -61,8 +61,8 @@ class TeamModel { * @param int $id * @return TeamInfo[] */ - public function listByName(string $name,int $id): array { - return $this->teams->listByName($name,$id); + public function listByName(string $name, int $id): array { + return $this->teams->listByName($name, $id); } /** @@ -71,7 +71,7 @@ class TeamModel { * @return Team|null */ public function getTeam(int $idTeam, int $idCurrentUser): ?Team { - if(!$this->members->isMemberOfTeam($idTeam,$idCurrentUser)){ + if(!$this->members->isMemberOfTeam($idTeam, $idCurrentUser)) { return null; } $teamInfo = $this->teams->getTeamById($idTeam); @@ -87,7 +87,7 @@ class TeamModel { */ public function deleteMember(int $idMember, int $teamId): int { $this->members->remove($teamId, $idMember); - if(empty($this->members->getMembersOfTeam($teamId))){ + if(empty($this->members->getMembersOfTeam($teamId))) { $this->teams->deleteTeam($teamId); return -1; } @@ -100,8 +100,8 @@ class TeamModel { * @param int $idTeam * @return int */ - public function deleteTeam(string $email, int $idTeam): int{ - if($this->members->isCoach($email,$idTeam)){ + public function deleteTeam(string $email, int $idTeam): int { + if($this->members->isCoach($email, $idTeam)) { $this->teams->deleteTeam($idTeam); return 0; } @@ -114,9 +114,9 @@ class TeamModel { * @param string $email * @return bool */ - public function isCoach(int $idTeam, string $email): bool{ - return $this->members->isCoach($email,$idTeam); - } + public function isCoach(int $idTeam, string $email): bool { + return $this->members->isCoach($email, $idTeam); + } /** * Edit a team with its id, and replace the current attributes with the new ones @@ -127,8 +127,8 @@ class TeamModel { * @param string $newSecondColor * @return void */ - public function editTeam(int $idTeam,string $newName,string $newPicture, string $newMainColor, string $newSecondColor){ - $this->teams->editTeam($idTeam,$newName,$newPicture, $newMainColor, $newSecondColor); - } + public function editTeam(int $idTeam, string $newName, string $newPicture, string $newMainColor, string $newSecondColor) { + $this->teams->editTeam($idTeam, $newName, $newPicture, $newMainColor, $newSecondColor); + } } -- 2.36.3 From 5ff028229d90099b8e34d548a172b1aec8027287 Mon Sep 17 00:00:00 2001 From: maxime Date: Mon, 8 Jan 2024 22:45:51 +0100 Subject: [PATCH 16/22] rm unused Ball.tsx --- front/model/tactic/Ball.ts | 17 ----------------- front/model/tactic/CourtObjects.ts | 4 ++-- 2 files changed, 2 insertions(+), 19 deletions(-) delete mode 100644 front/model/tactic/Ball.ts diff --git a/front/model/tactic/Ball.ts b/front/model/tactic/Ball.ts deleted file mode 100644 index 28e4830..0000000 --- a/front/model/tactic/Ball.ts +++ /dev/null @@ -1,17 +0,0 @@ -export type CourtObject = { type: "ball" } & Ball - -export interface Ball { - /** - * The ball is a "ball" court object - */ - readonly type: "ball" - - /** - * Percentage of the player's position to the bottom (0 means top, 1 means bottom, 0.5 means middle) - */ - readonly bottomRatio: number - /** - * Percentage of the player's position to the right (0 means left, 1 means right, 0.5 means middle) - */ - readonly rightRatio: number -} diff --git a/front/model/tactic/CourtObjects.ts b/front/model/tactic/CourtObjects.ts index 28e4830..56316d2 100644 --- a/front/model/tactic/CourtObjects.ts +++ b/front/model/tactic/CourtObjects.ts @@ -1,6 +1,6 @@ -export type CourtObject = { type: "ball" } & Ball +export type CourtObject = { type: "ball" } & CourtObjects -export interface Ball { +export interface CourtObjects { /** * The ball is a "ball" court object */ -- 2.36.3 From 1ac81d7349a2dbad33459bf6a4e76de8f701d103 Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 8 Jan 2024 23:01:14 +0100 Subject: [PATCH 17/22] removed unsed class Color --- front/model/team/Team.ts | 8 ++--- front/views/TeamPanel.tsx | 6 ++-- src/App/Views/edit_team.html.twig | 4 +-- src/Core/Data/Color.php | 50 ------------------------------- src/Core/Data/TeamInfo.php | 14 ++++----- src/Core/Gateway/TeamGateway.php | 5 ++-- src/Core/Model/TeamModel.php | 1 - 7 files changed, 16 insertions(+), 72 deletions(-) delete mode 100755 src/Core/Data/Color.php diff --git a/front/model/team/Team.ts b/front/model/team/Team.ts index 3a7f983..01a9d10 100644 --- a/front/model/team/Team.ts +++ b/front/model/team/Team.ts @@ -2,12 +2,8 @@ export interface TeamInfo { id: number name: string picture: string - mainColor: Color - secondColor: Color -} - -export interface Color { - hex: string + mainColor: string + secondColor: string } export interface Team { diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 66826b0..2afcc34 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -1,6 +1,6 @@ import "../style/team_panel.css" import { BASE } from "../Constants" -import { Team, TeamInfo, Color, User, Member } from "../model/team/Team" +import { Team, TeamInfo, User, Member } from "../model/team/Team" export default function TeamPanel({ isCoach, @@ -53,8 +53,8 @@ function TeamDisplay({ team }: { team: TeamInfo }) { ) } -function ColorDisplay({ color }: { color: Color }) { - return
+function ColorDisplay({ color }: { color: string }) { + return
} function CoachOptions({ id }: { id: number }) { diff --git a/src/App/Views/edit_team.html.twig b/src/App/Views/edit_team.html.twig index 00eef84..409d71a 100644 --- a/src/App/Views/edit_team.html.twig +++ b/src/App/Views/edit_team.html.twig @@ -67,9 +67,9 @@ - + - +
diff --git a/src/Core/Data/Color.php b/src/Core/Data/Color.php deleted file mode 100755 index f6244cd..0000000 --- a/src/Core/Data/Color.php +++ /dev/null @@ -1,50 +0,0 @@ -hex = $value; - } - - /** - * @return string - */ - public function getValue(): string { - return $this->hex; - } - - public static function from(string $value): Color { - $color = self::tryFrom($value); - if ($color == null) { - - throw new InvalidArgumentException("The string is not an hexadecimal code"); - } - return $color; - } - - public static function tryFrom(string $value): ?Color { - if (!preg_match('/#(?:[0-9a-fA-F]{6})/', $value)) { - return null; - } - return new Color($value); - } - - public function jsonSerialize() { - return get_object_vars($this); - } - - -} diff --git a/src/Core/Data/TeamInfo.php b/src/Core/Data/TeamInfo.php index 63b6a99..0f741fe 100644 --- a/src/Core/Data/TeamInfo.php +++ b/src/Core/Data/TeamInfo.php @@ -6,17 +6,17 @@ class TeamInfo implements \JsonSerializable { private int $id; private string $name; private string $picture; - private Color $mainColor; - private Color $secondColor; + private string $mainColor; + private string $secondColor; /** * @param int $id * @param string $name * @param string $picture - * @param Color $mainColor - * @param Color $secondColor + * @param string $mainColor + * @param string $secondColor */ - public function __construct(int $id, string $name, string $picture, Color $mainColor, Color $secondColor) { + public function __construct(int $id, string $name, string $picture, string $mainColor, string $secondColor) { $this->id = $id; $this->name = $name; $this->picture = $picture; @@ -37,11 +37,11 @@ class TeamInfo implements \JsonSerializable { return $this->picture; } - public function getMainColor(): Color { + public function getMainColor(): string { return $this->mainColor; } - public function getSecondColor(): Color { + public function getSecondColor(): string { return $this->secondColor; } diff --git a/src/Core/Gateway/TeamGateway.php b/src/Core/Gateway/TeamGateway.php index 9804e6b..71df931 100644 --- a/src/Core/Gateway/TeamGateway.php +++ b/src/Core/Gateway/TeamGateway.php @@ -3,7 +3,6 @@ namespace IQBall\Core\Gateway; use IQBall\Core\Connection; -use IQBall\Core\Data\Color; use IQBall\Core\Data\TeamInfo; use PDO; @@ -47,7 +46,7 @@ class TeamGateway { "id" => [$id, PDO::PARAM_INT], ] ); - return array_map(fn($row) => new TeamInfo($row['id'], $row['name'], $row['picture'], Color::from($row['main_color']), Color::from($row['second_color'])), $result); + return array_map(fn($row) => new TeamInfo($row['id'], $row['name'], $row['picture'], $row['main_color'], $row['second_color']), $result); } /** @@ -64,7 +63,7 @@ class TeamGateway { if ($row == null) { return null; } - return new TeamInfo($row['id'], $row['name'], $row['picture'], Color::from($row['main_color']), Color::from($row['second_color'])); + return new TeamInfo($row['id'], $row['name'], $row['picture'], $row['main_color'], $row['second_color']); } /** diff --git a/src/Core/Model/TeamModel.php b/src/Core/Model/TeamModel.php index 9e2821a..9f03953 100644 --- a/src/Core/Model/TeamModel.php +++ b/src/Core/Model/TeamModel.php @@ -2,7 +2,6 @@ namespace IQBall\Core\Model; -use IQBall\Core\Data\Color; use IQBall\Core\Data\Team; use IQBall\Core\Data\TeamInfo; use IQBall\Core\Gateway\AccountGateway; -- 2.36.3 From 429823093841578d8f32343e89b0a41910a52981 Mon Sep 17 00:00:00 2001 From: maxime Date: Mon, 8 Jan 2024 22:45:51 +0100 Subject: [PATCH 18/22] rm unused Ball.tsx --- front/components/editor/BasketCourt.tsx | 2 +- front/components/editor/CourtBall.tsx | 2 +- front/model/tactic/CourtObjects.ts | 17 ----------------- front/model/tactic/Tactic.ts | 2 +- front/views/Editor.tsx | 2 +- 5 files changed, 4 insertions(+), 21 deletions(-) delete mode 100644 front/model/tactic/CourtObjects.ts diff --git a/front/components/editor/BasketCourt.tsx b/front/components/editor/BasketCourt.tsx index d7f9ecb..525e232 100644 --- a/front/components/editor/BasketCourt.tsx +++ b/front/components/editor/BasketCourt.tsx @@ -14,7 +14,7 @@ import { Action, ActionKind } from "../../model/tactic/Action" import ArrowAction from "../actions/ArrowAction" import { middlePos, ratioWithinBase } from "../arrows/Pos" import BallAction from "../actions/BallAction" -import { CourtObject } from "../../model/tactic/CourtObjects" +import { CourtObject } from "../../model/tactic/Ball" import { contains } from "../arrows/Box" import { CourtAction } from "../../views/editor/CourtAction" diff --git a/front/components/editor/CourtBall.tsx b/front/components/editor/CourtBall.tsx index 1e0f9c8..b1fa1d0 100644 --- a/front/components/editor/CourtBall.tsx +++ b/front/components/editor/CourtBall.tsx @@ -1,7 +1,7 @@ import React, { useRef } from "react" import Draggable from "react-draggable" import { BallPiece } from "./BallPiece" -import { Ball } from "../../model/tactic/CourtObjects" +import { Ball } from "../../model/tactic/Ball" export interface CourtBallProps { onMoved: (rect: DOMRect) => void diff --git a/front/model/tactic/CourtObjects.ts b/front/model/tactic/CourtObjects.ts deleted file mode 100644 index 28e4830..0000000 --- a/front/model/tactic/CourtObjects.ts +++ /dev/null @@ -1,17 +0,0 @@ -export type CourtObject = { type: "ball" } & Ball - -export interface Ball { - /** - * The ball is a "ball" court object - */ - readonly type: "ball" - - /** - * Percentage of the player's position to the bottom (0 means top, 1 means bottom, 0.5 means middle) - */ - readonly bottomRatio: number - /** - * Percentage of the player's position to the right (0 means left, 1 means right, 0.5 means middle) - */ - readonly rightRatio: number -} diff --git a/front/model/tactic/Tactic.ts b/front/model/tactic/Tactic.ts index 296c339..2eab85b 100644 --- a/front/model/tactic/Tactic.ts +++ b/front/model/tactic/Tactic.ts @@ -1,5 +1,5 @@ import { Player } from "./Player" -import { CourtObject } from "./CourtObjects" +import { CourtObject } from "./Ball" import { Action } from "./Action" export interface Tactic { diff --git a/front/views/Editor.tsx b/front/views/Editor.tsx index 5a7ec30..e1f0edd 100644 --- a/front/views/Editor.tsx +++ b/front/views/Editor.tsx @@ -27,7 +27,7 @@ import SavingState, { SaveStates, } from "../components/editor/SavingState" -import { CourtObject } from "../model/tactic/CourtObjects" +import { CourtObject } from "../model/tactic/Ball" import { CourtAction } from "./editor/CourtAction" import { BasketCourt } from "../components/editor/BasketCourt" import { ratioWithinBase } from "../components/arrows/Pos" -- 2.36.3 From 00efd0f43d889c4d8a34ccdb12be5a2e4cb232c0 Mon Sep 17 00:00:00 2001 From: "mael.daim" Date: Mon, 8 Jan 2024 23:16:05 +0100 Subject: [PATCH 19/22] applied reviews changes --- front/style/team_panel.css | 26 +++++++++++--------------- front/views/TeamPanel.tsx | 20 ++++++++++---------- public/index.php | 2 +- src/App/Controller/TeamController.php | 25 ++++++++++++------------- 4 files changed, 34 insertions(+), 39 deletions(-) diff --git a/front/style/team_panel.css b/front/style/team_panel.css index bb573ff..6e48795 100644 --- a/front/style/team_panel.css +++ b/front/style/team_panel.css @@ -1,11 +1,11 @@ -#mainDiv { +#main-div { display: flex; flex-direction: column; align-items: center; height: 100%; } -header { +#main-div header { display: flex; justify-content: center; background-color: #525252; @@ -25,11 +25,7 @@ header h1 a { border: 2px white solid; } -#main_color { - border: solid; -} - -#teamInfo { +#team-info { display: flex; flex-direction: column; align-items: center; @@ -39,13 +35,13 @@ header h1 a { border-radius: 10px; } -#firstPart { +#first-part { display: flex; flex-direction: column; align-items: center; } -#teamName { +#team-name { font-size: 2.8em; } @@ -67,7 +63,7 @@ header h1 a { color: white; } -#actualColors { +#actual-colors { display: flex; flex-direction: row; justify-content: space-around; @@ -97,21 +93,21 @@ header h1 a { margin-bottom: 10px; } -#headMembers { +#head-members { width: 33%; display: flex; flex-direction: row; justify-content: space-evenly; } -#addMember { +#add-member { height: 30px; aspect-ratio: 1/1; border-radius: 100%; align-self: center; } -#Members { +#members { display: flex; flex-direction: column; background-color: #bcbcbc; @@ -121,7 +117,7 @@ header h1 a { border-radius: 10px; } -.Member { +.member { width: 60%; background-color: white; display: flex; @@ -133,7 +129,7 @@ header h1 a { margin-bottom: 5px; } -#profilePicture { +#profile-picture { height: 40px; width: 40px; } diff --git a/front/views/TeamPanel.tsx b/front/views/TeamPanel.tsx index 2afcc34..6d873c8 100644 --- a/front/views/TeamPanel.tsx +++ b/front/views/TeamPanel.tsx @@ -12,7 +12,7 @@ export default function TeamPanel({ currentUserId: number }) { return ( -
+

IQBall @@ -34,9 +34,9 @@ export default function TeamPanel({ function TeamDisplay({ team }: { team: TeamInfo }) { return ( -
-
-

{team.name}

+
+
+

{team.name}

@@ -44,7 +44,7 @@ function TeamDisplay({ team }: { team: TeamInfo }) {

Couleur principale

Couleur secondaire

-
+
@@ -100,12 +100,12 @@ function MembersDisplay({ /> )) return ( -
-
+
+

Membres :

{isCoach && (