Flexibilité sur la validation des vidéos accrue

This commit is contained in:
galaxyoyo 2019-09-19 00:31:53 +02:00
parent 1e67b8569d
commit 5372350f46
13 changed files with 289 additions and 17 deletions

View File

@ -16,6 +16,7 @@ class User
private $confirm_email;
private $forgotten_password;
private $inscription_date;
private $receive_animath_mails;
private function __construct() {}
@ -48,6 +49,21 @@ class User
$user->fill($data);
return $user;
}
public static function getAdmins()
{
global $DB, $YEAR;
$admins = [];
$req = $DB->query("SELECT * FROM `users` WHERE `year` = $YEAR;");
while (($data = $req->fetch()) !== false) {
$admin = new User();
$admin->fill($data);
$admins[] = $admin;
}
return $admins;
}
private function fill($data)
{
@ -65,6 +81,7 @@ class User
$this->confirm_email = $data["confirm_email"];
$this->forgotten_password = $data["forgotten_password"];
$this->inscription_date = $data["inscription_date"];
$this->receive_animath_mails = $data["receive_animath_mails"];
}
public function getEmail()
@ -170,7 +187,6 @@ class User
{
global $DB;
$this->role = $role;
/** @noinspection PhpUndefinedMethodInspection */
$DB->prepare("UPDATE `users` SET `role` = ? WHERE `id` = ?;")->execute([Role::getName($role), $this->getId()]);
}
@ -215,6 +231,18 @@ class User
return $this->inscription_date;
}
public function doReceiveAnimathMails()
{
return $this->receive_animath_mails;
}
public function setReceiveAnimathMails($receive_animath_mails)
{
global $DB;
$this->receive_animath_mails = $receive_animath_mails;
$DB->prepare("UPDATE `users` SET `receive_animath_mails` = ? WHERE `id` = ?;")->execute([$receive_animath_mails, $this->getId()]);
}
public function getAllDocuments($problem)
{
global $DB;

View File

@ -3,11 +3,16 @@
class Video
{
const NOT_CONTROLLED = 0;
const REJECTED = -1;
const ACCEPTED = 1;
private $id;
private $team;
private $problem;
private $link;
private $reason;
private $validation;
private $uploaded_at;
private $year;
private $version;
@ -29,14 +34,16 @@ class Video
return $video;
}
public static function getVideos($reason, $problem, $team_id = -1)
public static function getVideos($reason, $problem, $validation_min = -1, $team_id = -1)
{
global $DB;
global $DB, $YEAR;
$req = $DB->query("SELECT * FROM `videos` AS `t1` "
. "INNER JOIN (SELECT `team`, `problem`, `reason`, MAX(`uploaded_at`) AS `last_upload`, COUNT(`team`) AS `version` FROM `videos` GROUP BY `problem`, `reason`, `team`) `t2` "
. "INNER JOIN (SELECT `team`, `problem`, `reason`, MAX(`uploaded_at`) AS `last_upload`, COUNT(`team`) AS `version` FROM `videos` "
. "WHERE `validation` >= $validation_min AND `year` = $YEAR GROUP BY `problem`, `reason`, `team`) `t2` "
. "ON `t1`.`team` = `t2`.`team` AND `t1`.`reason` = `t2`.`reason` AND `t1`.`problem` = `t2`.`problem` "
. "WHERE `t1`.`uploaded_at` = `t2`.`last_upload` AND `t1`.`problem` = $problem AND `t1`.`reason` = '" . Reason::getName($reason) . "'"
. ($team_id >= 0 ? " AND `t1`.`team` = $team_id" : "") . " ORDER BY `t1`.`problem`, `t1`.`reason`;");
. ($team_id >= 0 ? " AND `t1`.`team` = $team_id" : "")
. " AND `validation` >= $validation_min AND `year` = $YEAR ORDER BY `t1`.`problem`, `t1`.`reason`;");
$videos = [];
@ -52,10 +59,11 @@ class Video
/**
* @param int $reason
* @param Team $team
* @param int $validation_min
* @return Video|null
*/
public static function getVideo($reason, Team $team) {
$videos = self::getVideos($reason, $team->getProblem(), $team->getId());
public static function getVideo($reason, Team $team, $validation_min = -1) {
$videos = self::getVideos($reason, $team->getProblem(), $validation_min, $team->getId());
if (sizeof($videos) == 0)
return null;
else
@ -95,6 +103,18 @@ class Video
return $this->reason;
}
public function getValidation()
{
return $this->validation;
}
public function setValidation($validation)
{
global $DB;
$this->validation = $validation;
$DB->exec("UPDATE `videos` SET `validation` = $validation WHERE `id` = $this->id;");
}
public function getUploadedAt()
{
return $this->uploaded_at;

View File

@ -22,17 +22,22 @@ if (isset($_POST["upload"])) {
class NewVideo
{
private $link;
public $link;
private $valid_link;
private $no_change;
public function __construct($data)
{
$this->link = $data["link"];
foreach ($data as $key => $value)
$this->$key = $value;
}
public function makeVerifications()
{
ensure(preg_match("#(https?\:\/\/|)[a-zA-Z0-9\-\.]+\.[a-zA-Z]{2,3}(\/\S*)?#", $this->link), "Ce n'est pas une URL valide.");
$this->link = preg_replace('/^(?!https?:\/\/)/', 'https://', $this->link);
ensure($this->valid_link != null, "Vous devez confirmer que le lien est valide.");
ensure($this->no_change != null, "Vous devez vous engager à ne pas changer le contenu du lien et de la vidéo.");
}
public function uploadVideo()
@ -41,9 +46,12 @@ class NewVideo
$req = $DB->prepare("INSERT INTO `videos`(`team`, `problem`, `link`, `reason`, `year`) VALUES (?, ?, ?, ?, ?)");
$req->execute([$team->getId(), $team->getProblem(), $this->link, "SOLUTION", $YEAR]);
Mailer::sendNewVideo($this, $team);
}
}
$video = Video::getVideo(Reason::SOLUTION, $team);
$video_validated = Video::getVideo(Reason::SOLUTION, $team, Video::ACCEPTED);
require_once "server_files/views/envoyer_video.php";

View File

@ -41,6 +41,7 @@ class MyAccount
public $school;
public $class;
public $description;
public $receive_animath_mails;
/** @var User */
private $user;
@ -65,6 +66,7 @@ class MyAccount
ensure(filter_var($this->email, FILTER_VALIDATE_EMAIL), "L'adresse e-mail entrée est invalide.");
$this->email = strtolower($this->email);
ensure($this->email == $this->user->getEmail() || !userExists($this->email), "Un compte existe déjà avec cette adresse e-mail.");
$this->receive_animath_mails = $this->receive_animath_mails != false;
}
public function updateAccount()
@ -74,6 +76,7 @@ class MyAccount
$this->user->setSchool($this->school);
$this->user->setClass($this->class);
$this->user->setDescription($this->description);
$this->user->setReceiveAnimathMails($this->receive_animath_mails);
if ($this->email != $this->user->getEmail()) {
$this->user->setEmail($this->email);

View File

@ -3,9 +3,54 @@
if (!isset($_SESSION["user_id"]) || $_SESSION["role"] != Role::ADMIN)
require_once "server_files/403.php";
$has_error = false;
$error_message = null;
if (isset($_POST["validate_video"])) {
$validate_video = new ValidateVideo($_POST);
try {
$validate_video->makeVerifications();
$validate_video->validate();
}
catch (AssertionError $e) {
$has_error = true;
$error_message = $e->getMessage();
}
}
class ValidateVideo
{
private $video_id;
private $accept;
private $reject;
/** @var Video */
private $video;
public function __construct($data)
{
foreach ($data as $key => $value)
$this->$key = $value;
}
public function makeVerifications()
{
$this->video = Video::fromId($this->video_id);
ensure($this->video != null, "La vidéo n'existe pas.");
ensure($this->video->getValidation() == 0, "La vidéo est déjà validée / rejetée.");
ensure(($this->accept == null || $this->reject == null) && $this->accept != $this->reject, "Impossible de déterminer s'il faut accepter ou non la vidéo.");
}
public function validate()
{
$this->video->setValidation($this->accept ? 1 : -1);
Mailer::validateVideo($this->video);
}
}
$videos = [];
for ($problem = 1; $problem <= 4; ++$problem)
$videos[] = Video::getVideos(Reason::SOLUTION, $problem);
require_once "server_files/views/videos_solutions.php";

View File

@ -53,7 +53,7 @@ function quitTeam()
/** @noinspection SqlResolve */
$DB->exec("UPDATE `teams` SET `participant_$i` = NULL WHERE `participant_$i` = $user_id;");
else
$DB->exec("UPDATE `teams` SET `encadrant` = NULL WHERE `encadrant` = $user_id;");
$DB->exec("UPDATE `teams` SET `encadrant` = NULL WHERE `encadrant` = $user_id;");
$user->setTeamId(null);
for ($i = 1; $i <= 4; ++$i) {
/** @noinspection SqlResolve */
@ -167,4 +167,12 @@ function getZipFile($problem, $team_id = -1)
$zip->close();
return $file_name;
}
function displayVideo($link)
{
if (preg_match("#(https?\://|)(www\.|)youtube\.com\/watch\?v=(.*)#", $link, $matches)) {
$code = $matches[3];
echo "<center><iframe width=\"854px\" height=\"480px\" src=\"https://www.youtube.com/embed/$code\" frameborder=\"0\" allow=\"accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen></iframe></center><br />\n";
}
}

View File

@ -16,6 +16,40 @@ class Mailer
ensure(mail($email, $subject, $content, $headers), "Un problème est survenu dans l'envoi d'un mail. Veuiller contacter votre administrateur.");
}
private static function broadcastToTeam(Team $team, $subject, $content, $from = "contact")
{
$content = preg_replace("#{TEAM_NAME}#", $team->getName(), $content);
$content = preg_replace("#{TRIGRAM}#", $team->getTrigram(), $content);
$encadrant = User::fromId($team->getEncadrantId());
if ($encadrant != null) {
$c = preg_replace("#{FIRST_NAME}#", $encadrant->getFirstName(), $content);
$c = preg_replace("#{SURNAME}#", $encadrant->getSurname(), $c);
self::sendMail($encadrant->getEmail(), $subject, $c, $from);
}
foreach ($team->getParticipants() as $participant_id) {
$participant = User::fromId($participant_id);
if ($participant == null)
continue;
$c = preg_replace("#{FIRST_NAME}#", $participant->getFirstName(), $content);
$c = preg_replace("#{SURNAME}#", $participant->getSurname(), $c);
self::sendMail($participant->getEmail(), $subject, $c, $from);
}
}
private static function broadcastToAdmins($subject, $content, $from = "contact")
{
/** @var User $admin */
foreach (User::getAdmins() as $admin) {
$c = preg_replace("#{FIRST_NAME}#", $admin->getFirstName(), $content);
$c = preg_replace("#{SURNAME}#", $admin->getSurname(), $c);
self::sendMail($admin->getEmail(), $subject, $c, $from);
}
}
private static function getTemplate($name)
{
global $LOCAL_PATH;
@ -115,4 +149,29 @@ class Mailer
self::sendMail($user->getEmail(), "Équipe rejointe Correspondances des Jeunes Mathématicien·ne·s $YEAR", $content);
}
public static function sendNewVideo(NewVideo $video, Team $team)
{
global $YEAR;
$content = self::getTemplate("new_video");
$content = preg_replace("#{TEAM_NAME}#", $team->getName(), $content);
$content = preg_replace("#{TRIGRAM}#", $team->getTrigram(), $content);
$content = preg_replace("#{PROBLEM}#", $team->getProblem(), $content);
$content = preg_replace("#{VIDEO_LINK}#", $video->link, $content);
self::broadcastToAdmins("Nouvelle vidéo Correspondances des Jeunes Mathématicien·ne·s $YEAR", $content);
}
public static function validateVideo(Video $video)
{
global $YEAR;
$team = Team::fromId($video->getTeam());
$content = self::getTemplate($video->getValidation() == Video::ACCEPTED ? "video_accepted" : "video_rejected");
$content = preg_replace("#{TRIGRAM}#", $team->getTrigram(), $content);
$content = preg_replace("#{PROBLEM}#", $team->getProblem(), $content);
$content = preg_replace("#{VIDEO_LINK}#", $video->getLink(), $content);
self::broadcastToTeam($team, ($video->getValidation() == Video::REJECTED ? "Vidéo refusée " : "Vidéo acceptée ") . $team->getTrigram() . " Correspondances des Jeunes Mathématicien·ne·s $YEAR", $content);
}
}

View File

@ -0,0 +1,18 @@
<!DOCTYPE html>
<html lang="fr">
<head>
<meta charset="UTF-8">
<title>Nouvelle vidéo Correspondances des Jeunes Mathématicien·ne·s {YEAR}</title>
</head>
<body>
Bonjour {FIRST_NAME} {SURNAME},<br/>
<br/>
L'équipe « {TEAM_NAME} » ({TRIGRAM}) vient d'ajouter une vidéo pour le problème {PROBLEM} des Correspondances des Jeunes Mathématicien·ne·s : <a href="{VIDEO_LINK}">{VIDEO_LINK}</a>.
Vous êtes désormais invité avant que quelqu'un d'autre ne le fasse à accepter ou refuser cette vidéo via la plateforme d'inscription (accessible après connexion) :
<a href="{URL_BASE}/videos-solutions">{URL_BASE}/videos-solutions</a><br/>
<br/>
Cordialement,<br/>
<br/>
Le comité d'organisation des Correspondances des Jeunes Mathématicien·ne·s
</body>
</html>

View File

@ -0,0 +1,18 @@
<!DOCTYPE html>
<html lang="fr">
<head>
<meta charset="UTF-8">
<title>Vidéo acceptée Correspondances des Jeunes Mathématicien·ne·s {YEAR}</title>
</head>
<body>
Bonjour {FIRST_NAME} {SURNAME},<br/>
<br/>
Félicitations, votre vidéo pour le problème {PROBLEM} a été validée ! Pour rappel, vous aviez soumis ce lien : <a href="{VIDEO_LINK}">{VIDEO_LINK}</a>.<br />
Votre travail est à présent terminé, et vous pouvez attendre les prochaines phases. Bravo à vous !<br />
Si toutefois vous le souhaitez, vous pouvez à nouveau soumettre une vidéo avant la fin de la phase. Cette nouvelle vidéo ne remplacera l'actuelle qu'au moment de la validation de celle-ci.<br />
<br/>
Cordialement,<br/>
<br/>
Le comité d'organisation des Correspondances des Jeunes Mathématicien·ne·s
</body>
</html>

View File

@ -0,0 +1,19 @@
<!DOCTYPE html>
<html lang="fr">
<head>
<meta charset="UTF-8">
<title>Vidéo refusée Correspondances des Jeunes Mathématicien·ne·s {YEAR}</title>
</head>
<body>
Bonjour {FIRST_NAME} {SURNAME},<br/>
<br/>
Malheureusement, votre vidéo pour le problème {PROBLEM} n'a pas été validée. Pour rappel, vous aviez soumis ce lien : <a href="{VIDEO_LINK}">{VIDEO_LINK}</a>.<br />
Si vous aviez soumis une précédente vidéo qui a été validée, elle reste conservée.
Vous êtes désormais invités à retravailler vos résultats ou votre présentation orale afin que votre prestation soit validée par les organisateurs.
N'hésitez pas à nous contacter à <a href="mailto:contact@correspondances-maths.fr">contact@correspondances-maths.fr</a> si vous souhaitez avoir plus d'informations ou contester ce refus.
<br/>
Cordialement,<br/>
<br/>
Le comité d'organisation des Correspondances des Jeunes Mathématicien·ne·s
</body>
</html>

View File

@ -12,11 +12,24 @@ elseif (isset($new_video))
if ($video !== null) {
$link = $video->getLink();
echo "Lien de la vidéo déjà envoyée : <a href=\"$link\">$link</a> (version " . $video->getVersion() . ")<br />\n";
if (preg_match("#(https?\://|)(www\.|)youtube\.com\/watch\?v=(.*)#", $link, $matches)) {
$code = $matches[3];
echo "<center><iframe width=\"854px\" height=\"480px\" src=\"https://www.youtube.com/embed/$code\" frameborder=\"0\" allow=\"accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen></iframe></center><br />\n";
displayVideo($link);
switch ($video->getValidation()) {
case 0:
echo "La vidéo n'a pas encore été contrôlée.<br />";
break;
case 1:
echo "La vidéo a été acceptée.<br />";
break;
case -1:
echo "La vidéo a été rejetée.<br />";
break;
}
}
if ($video_validated != null && $video_validated->getId() != $video->getId()) {
$link = $video_validated->getLink();
echo "<hr />\nLien de la dernière vidéo validée : <a href=\"$link\">$link</a><br />";
displayVideo($link);
}
?>
<form method="POST">
@ -30,6 +43,16 @@ if ($video !== null) {
<input style="width: 100%;" type="url" id="link" name="link" />
</td>
</tr>
<tr>
<td style="text-align: center;" colspan="2">
<input type="checkbox" name="valid_link" id="valid_link" required /> <label for="valid_link">Je confirme que le lien est valide</label>
</td>
</tr>
<tr>
<td style="text-align: center;" colspan="2">
<input type="checkbox" name="no_change" id="no_change" required /> <label for="no_change">Je m'engage à ne pas changer le contenu du lien et de la vidéo</label>
</td>
</tr>
<tr>
<td colspan="2">
<input style="width: 100%;" type="submit" name="upload" value="Envoyer la vidéo" />

View File

@ -60,6 +60,9 @@ elseif (isset($my_account) || isset($new_password)) {
<td><textarea style="width: 100%" id="description" name="description"><?= $user->getDescription() ?></textarea></td>
</tr>
<?php } ?>
<tr>
<td style="text-align: center;" colspan="2"><input type="checkbox" id="receive_animath_mails" name="receive_animath_mails" <?= $user->doReceiveAnimathMails() ? "checked" : "" ?> /> <label for="receive_animath_mails">J'accepte de recevoir des mails de la part d'Animath</label></td>
</tr>
<tr>
<td colspan="2"><input type="submit" style="width: 100%" value="Mettre à jour mes données"/></td>
</tr>

View File

@ -2,6 +2,10 @@
require_once "header.php";
if ($has_error) {
echo "<h2>Erreur : $error_message</h2>";
}
for ($problem = 1; $problem <= 4; ++$problem) {
echo "<h2>Vidéos pour le problème $problem</h2>\n";
/** @var Video $video */
@ -9,10 +13,26 @@ for ($problem = 1; $problem <= 4; ++$problem) {
$link = $video->getLink();
$team = Team::fromId($video->getTeam());
$version = $video->getVersion();
echo "Vidéo de présentation de l'équipe « " . $team->getName() . " » (" . $team->getTrigram() . "), version $version : <a href=\"$link\">$link</a>\n";
if (preg_match("#(https?\://|)(www\.|)youtube\.com\/watch\?v=(.*)#", $link, $matches)) {
$code = $matches[3];
echo "<center><iframe width=\"854px\" height=\"480px\" src=\"https://www.youtube.com/embed/$code\" frameborder=\"0\" allow=\"accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen></iframe></center><br />\n";
echo "<h4>Vidéo de présentation de l'équipe « " . $team->getName() . " » (" . $team->getTrigram() . ") :</h4>\n";
echo "Lien de la vidéo (version $version) : <a href=\"$link\">$link</a>";
displayVideo($link);
if ($video->getValidation() == 0) { ?>
<form method="POST">
<input type="hidden" name="validate_video" value="" />
<input type="hidden" name="video_id" value="<?= $video->getId() ?>" />
<input style="width: 49%;" type="submit" name="accept" value="Accepter la vidéo" />
<input style="width: 49%;" type="submit" name="reject" value="Refuser la vidéo" />
</form>
<?php }
else
echo "<h5>La vidéo a été " . ($video->getValidation() == 1 ? "acceptée" : "refusée") . ".</h5><br />\n";
if ($video->getValidation() != Video::ACCEPTED) {
$last_validated_video = Video::getVideo(Reason::SOLUTION, $team, Video::ACCEPTED);
$link = $last_validated_video->getLink();
echo "\nLien de la dernière vidéo validée de cette équipe : <a href=\"$link\">$link</a><br />\n";
displayVideo($link);
}
}
echo "<hr />\n";