From e6e534120a4a3a015dda82fe1c25d7fe153fae3c Mon Sep 17 00:00:00 2001
From: Sofiane Lasri-Trienpont <alasri250@gmail.com>
Date: Mon, 7 Mar 2022 20:30:58 +0100
Subject: [PATCH] 1.5.1

---
 pom.xml                                       |   2 +-
 .../com/slprojects/slcraftplugin/Main.java    | 182 +-------------
 .../tachesParalleles/savePlayerData.java      | 227 ++++++++++++++++++
 .../tachesParalleles/waitForDiscordMsg.java   |   3 +-
 src/main/resources/config.yml                 |   2 +-
 .../com/slprojects/slcraftplugin/Main.class   | Bin 17345 -> 11407 bytes
 target/classes/config.yml                     |   2 +-
 target/classes/plugin.yml                     |   2 +-
 target/maven-archiver/pom.properties          |   4 +-
 9 files changed, 244 insertions(+), 180 deletions(-)
 create mode 100644 src/main/java/com/slprojects/slcraftplugin/tachesParalleles/savePlayerData.java

diff --git a/pom.xml b/pom.xml
index 8855c8e..606f947 100644
--- a/pom.xml
+++ b/pom.xml
@@ -6,7 +6,7 @@
 
     <groupId>com.slprojects</groupId>
     <artifactId>SLCraftPlugin</artifactId>
-    <version>1.5</version>
+    <version>1.5.1</version>
     <packaging>jar</packaging>
 
     <name>SLCraftPlugin</name>
diff --git a/src/main/java/com/slprojects/slcraftplugin/Main.java b/src/main/java/com/slprojects/slcraftplugin/Main.java
index 3f90255..1d292c0 100644
--- a/src/main/java/com/slprojects/slcraftplugin/Main.java
+++ b/src/main/java/com/slprojects/slcraftplugin/Main.java
@@ -4,11 +4,11 @@ package com.slprojects.slcraftplugin;
 
 import com.slprojects.slcraftplugin.commandes.linkCodeCommand;
 import com.slprojects.slcraftplugin.commandes.wildCommand;
+import com.slprojects.slcraftplugin.tachesParalleles.savePlayerData;
 import com.slprojects.slcraftplugin.tachesParalleles.waitForDiscordMsg;
 import me.clip.placeholderapi.PlaceholderAPI;
 import org.bukkit.ChatColor;
 import org.bukkit.Sound;
-import org.bukkit.Statistic;
 import org.bukkit.configuration.file.FileConfiguration;
 import org.bukkit.entity.Player;
 import org.bukkit.event.EventHandler;
@@ -29,24 +29,17 @@ import java.net.URL;
 import java.net.URLEncoder;
 import java.sql.Connection;
 import java.sql.PreparedStatement;
-import java.sql.ResultSet;
 import java.sql.SQLException;
-import java.time.Duration;
-import java.time.LocalDateTime;
-import java.time.ZoneOffset;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.UUID;
 import java.util.concurrent.TimeUnit;
 
-import static java.lang.Integer.parseInt;
-
 public final class Main extends JavaPlugin implements Listener {
     // Variables
     private List<UUID> wildCommandActiveUsers;
-    private List<UUID> playTimeUsersIndexes;
-    private List<LocalDateTime> playTimeUsersDate;
     private static FileConfiguration config;
+    private com.slprojects.slcraftplugin.tachesParalleles.savePlayerData savePlayerData;
 
     // Fonctions appelées à des évènements clés
     @Override
@@ -65,13 +58,12 @@ public final class Main extends JavaPlugin implements Listener {
         saveDefaultConfig();
         reloadConfig();
         config = getConfig();
+        savePlayerData = new savePlayerData(this);
 
         // On initialise la base de donnée
         initDatabase();
 
         wildCommandActiveUsers = new ArrayList<>();
-        playTimeUsersIndexes = new ArrayList<>();
-        playTimeUsersDate = new ArrayList<>();
         wildCommand wildCommand = new wildCommand(this);
         getCommand("wild").setExecutor(wildCommand);
 
@@ -88,13 +80,14 @@ public final class Main extends JavaPlugin implements Listener {
         // Plugin shutdown logic
         getLogger().info(ChatColor.RED+"SL-Craft | Plugin éteint");
 
-        getServer().getOnlinePlayers().forEach(this::savePlayer);
+        getServer().getOnlinePlayers().forEach(player -> {
+            savePlayerData.saveOnQuit(player);
+        });
     }
 
     @EventHandler(priority = EventPriority.HIGHEST)
     public void onPlayerJoin(PlayerJoinEvent e) {
-        playTimeUsersIndexes.add(e.getPlayer().getUniqueId());
-        playTimeUsersDate.add(LocalDateTime.now());
+        savePlayerData.saveOnJoin(e.getPlayer());
 
         // On affiche le message de bienvenue
         String welcomeMessage = PlaceholderAPI.setPlaceholders(e.getPlayer(), getConfig().getString("player-join-message"));
@@ -110,7 +103,7 @@ public final class Main extends JavaPlugin implements Listener {
 
     @EventHandler(priority = EventPriority.HIGHEST)
     public void onPlayerQuit(PlayerQuitEvent e) {
-        savePlayer(e.getPlayer());
+        savePlayerData.saveOnQuit(e.getPlayer());
         String quitMessage = PlaceholderAPI.setPlaceholders(e.getPlayer(), getConfig().getString("player-quit-message"));
         for(Player p : getServer().getOnlinePlayers()){
             p.sendMessage(quitMessage);
@@ -118,7 +111,7 @@ public final class Main extends JavaPlugin implements Listener {
     }
 
     // On renvoie chaque message des joueurs sur le canal de chat du serveur discord
-    @SuppressWarnings("unchecked")
+    @SuppressWarnings({"unchecked", "deprecation"})
     @EventHandler(priority = EventPriority.LOWEST)
     void AsyncChatEvent(AsyncPlayerChatEvent e) throws UnsupportedEncodingException {
         // On va appeler l'api du bot discord
@@ -127,7 +120,6 @@ public final class Main extends JavaPlugin implements Listener {
         json.put("username", e.getPlayer().getName());
 
         String urlString = "http://node.sl-projects.com:27001/mc/chat/" + URLEncoder.encode(json.toJSONString(), "UTF-8").replace("+", "%20");
-        getLogger().info(urlString);
         // Processus long et chiant
         try {
             URL url = new URL(urlString);
@@ -157,162 +149,6 @@ public final class Main extends JavaPlugin implements Listener {
         }
     }
 
-    // Propre au compteur de temps de jeu
-    @SuppressWarnings("unchecked")
-    public void savePlayer(Player player) {
-        JSONObject target = new JSONObject();
-        // On ajoute l'uuid et son nom
-        target.put("uuid", player.getUniqueId().toString());
-        target.put("name", player.getName());
-        
-        // La date de join (locale, au cas où CoreProtect ne l'a pas)
-        target.put("joinedDate", playTimeUsersDate.get(playTimeUsersIndexes.indexOf(player.getUniqueId())).toString());
-
-        // On calcule le temps de jeu
-        LocalDateTime timeNow = LocalDateTime.now();
-        Duration duration = Duration.between(timeNow, playTimeUsersDate.get(playTimeUsersIndexes.indexOf(player.getUniqueId())));
-        long playedTimeInSeconds = Math.abs(duration.toSeconds());
-
-        // On ajoute le temps de jeu au joueur
-        target.put("playedTime", playedTimeInSeconds);
-
-        playTimeUsersDate.remove(playTimeUsersIndexes.indexOf(player.getUniqueId()));
-        playTimeUsersIndexes.remove(player.getUniqueId());
-
-        target.put("joins", player.getStatistic(Statistic.LEAVE_GAME) + 1);
-        target.put("hasPlayedBefore", player.hasPlayedBefore());
-        writePlayer(target);
-    }
-
-    private void writePlayer(JSONObject target) {
-        // On ouvre la bdd
-        Connection con = bddOpenConn();
-        try {
-            // On va regarder si Le joueur existe
-            PreparedStatement rechercheUtilisateur = con.prepareStatement("SELECT COUNT(*) FROM site_userSetting WHERE uuid = ?");
-            rechercheUtilisateur.setString(1, target.get("uuid").toString());
-            ResultSet resultat = rechercheUtilisateur.executeQuery();
-            if(resultat.next()) {
-                int playerExist = resultat.getInt(1);
-
-                if(playerExist==0){
-                    // On insère la dernière date de join
-                    PreparedStatement insertionLastJoin = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'playedTime',?)");
-                    insertionLastJoin.setString(1, target.get("uuid").toString());
-                    insertionLastJoin.setString(2, target.get("playedTime").toString());
-                    insertionLastJoin.executeQuery();
-
-                    // On insère le nombre de connexions
-                    PreparedStatement insertionNbJoins = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joins',?)");
-                    insertionNbJoins.setString(1, target.get("uuid").toString());
-                    insertionNbJoins.setString(2, target.get("joins").toString());
-                    insertionNbJoins.executeQuery();
-
-                    // On va regarder si Le joueur a déjà joué avant (vu qu'on avait pas de données sur ce joueur)
-                    if(target.get("hasPlayedBefore").toString().equals("true")){
-                        // On va piocher la date d'inscription chez CoreProtect (si elle existe)
-                        // On la prend chez CoreProtect car le plugin a été installé dans les premières semaines du serveur. Il a donc bcp plus de données que nous concernant les anciens joueurs.
-                        PreparedStatement rechercheDateInscription = con.prepareStatement("SELECT time FROM co_user WHERE uuid = ?");
-                        rechercheDateInscription.setString(1, target.get("uuid").toString());
-                        resultat = rechercheDateInscription.executeQuery();
-
-                        if(resultat.next()){
-                            // On insère la date d'inscription
-                            PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
-                            insertionDateInscription.setString(1, target.get("uuid").toString());
-                            insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(LocalDateTime.ofEpochSecond(Long.parseLong(resultat.getString("time")), 0, ZoneOffset.UTC)).toString()); // Il faut convertir le timestamp (epoch second) en date
-                            insertionDateInscription.executeQuery();
-
-                            // On va précisier que la date d'inscription a été trouvée chez CoreProtect
-                            getLogger().info("Le joueur "+ChatColor.GOLD+target.get("name").toString()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs. On lui a donc attribué comme date de création du compte, celle que détenait CoreProtect.");
-                        } else {
-                            // On insère la date d'inscription (du coup on considère que Le joueur n'a pas joué avant, malgré la condition)
-                            PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
-                            insertionDateInscription.setString(1, target.get("uuid").toString());
-                            insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(target.get("joinedDate").toString()).toString());
-                            insertionDateInscription.executeQuery();
-                            
-                            // On va préciser que la date d'inscription n'a pas été trouvée chez CoreProtect
-                            PreparedStatement insertionInaccurrateJoinedDate = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'inaccurrateJoinedDate',?)");
-                            insertionInaccurrateJoinedDate.setString(1, target.get("uuid").toString());
-                            insertionInaccurrateJoinedDate.setString(2, "true");
-                            insertionInaccurrateJoinedDate.executeQuery();
-                            
-                            getLogger().info("Le joueur "+ChatColor.GOLD+target.get("name").toString()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs, ni dans la table des utilisateurs de CoreProtect. On lui a donc attribué comme date de création du compte, la date du début de sa partie.");
-                        }
-                    }else{
-                        // C'est un nouvel utilisateur, on peut lui attribuer la date d'inscription précédement calculée
-                        PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
-                        insertionDateInscription.setString(1, target.get("uuid").toString());
-                        insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(target.get("joinedDate").toString()).toString());
-                        insertionDateInscription.executeQuery();
-                    }
-                }else{
-                    PreparedStatement tempsJeuJoueur = con.prepareStatement("SELECT value FROM site_userSetting WHERE uuid = ? AND name = 'playedTime'");
-                    tempsJeuJoueur.setString(1, target.get("uuid").toString());
-                    resultat = tempsJeuJoueur.executeQuery();
-                    if(resultat.next()) {
-                        int totalPlayedTime = parseInt(resultat.getString(1)) + parseInt(target.get("playedTime").toString());
-                        PreparedStatement modifyPlayedTime = con.prepareStatement("UPDATE `site_userSetting` SET `value`=? WHERE  `uuid`=? AND `name`='playedTime'");
-                        modifyPlayedTime.setInt(1, totalPlayedTime);
-                        modifyPlayedTime.setString(2, target.get("uuid").toString());
-                        modifyPlayedTime.executeQuery();
-
-                        PreparedStatement modifyNbJoins = con.prepareStatement("UPDATE `site_userSetting` SET `value`=? WHERE  `uuid`=? AND `name`='joins'");
-                        modifyNbJoins.setString(1, target.get("joins").toString());
-                        modifyNbJoins.setString(2, target.get("uuid").toString());
-                        modifyNbJoins.executeQuery();
-
-                        // On va regarder s'il a sa date d'inscription de renseignée
-                        PreparedStatement rechercheDateInscription = con.prepareStatement("SELECT * FROM site_userSetting WHERE uuid = ? AND name = 'joinedDate'");
-                        rechercheDateInscription.setString(1, target.get("uuid").toString());
-                        resultat = rechercheDateInscription.executeQuery();
-
-                        if(!resultat.next()){
-                            // On va regarder si l'on dispose de sa date d'inscription chez CoreProtect
-                            rechercheDateInscription = con.prepareStatement("SELECT time FROM co_user WHERE uuid = ?");
-                            rechercheDateInscription.setString(1, target.get("uuid").toString());
-                            resultat = rechercheDateInscription.executeQuery();
-
-                            if(resultat.next()){
-                                // On insère la date d'inscription
-                                PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
-                                insertionDateInscription.setString(1, target.get("uuid").toString());
-                                insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(LocalDateTime.ofEpochSecond(Long.parseLong(resultat.getString("time")), 0, ZoneOffset.UTC)).toString()); // Il faut convertir le timestamp (epoch second) en date
-                                insertionDateInscription.executeQuery();
-
-                                // On va précisier que la date d'inscription a été trouvée chez CoreProtect
-                                getLogger().info("Le joueur "+ChatColor.GOLD+target.get("name").toString()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs. On lui a donc attribué comme date de création du compte, celle que détenait CoreProtect.");
-                            } else {
-                                // On insère la date d'inscription (du coup, comme précédement, on prend la date d'inscription locale)
-                                PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
-                                insertionDateInscription.setString(1, target.get("uuid").toString());
-                                insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(target.get("joinedDate").toString()).toString());
-                                insertionDateInscription.executeQuery();
-
-                                // On va préciser que la date d'inscription n'a pas été trouvée chez CoreProtect
-                                PreparedStatement insertionInaccurrateJoinedDate = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'inaccurrateJoinedDate',?)");
-                                insertionInaccurrateJoinedDate.setString(1, target.get("uuid").toString());
-                                insertionInaccurrateJoinedDate.setString(2, "true");
-                                insertionInaccurrateJoinedDate.executeQuery();
-
-                                getLogger().info("Le joueur "+ChatColor.GOLD+target.get("name").toString()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs, ni dans la table des utilisateurs de CoreProtect. On lui a donc attribué comme date de création du compte, la date du début de sa partie.");
-                            }
-                        }
-
-                    }else{
-                        getLogger().warning(ChatColor.RED+"Erreur, nous n'avons pas de resultats pour la requête: SELECT value FROM site_userSetting WHERE uuid = '"+target.get("uuid")+"' AND name = playedTime");
-                    }
-                }
-            }else{
-                getLogger().warning(ChatColor.RED+"Erreur, nous n'avons pas de resultats pour la requête: SELECT COUNT(*) FROM site_userSetting WHERE uuid = '"+target.get("uuid").toString()+"' AND rownum = 1");
-            }
-            con.close();
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-    }
-
     // Propre à la commande wild: évite les spams de la commande
     public boolean checkActiveUserForWildCommand(UUID playerUuid){
         if(wildCommandActiveUsers.contains(playerUuid)){
diff --git a/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/savePlayerData.java b/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/savePlayerData.java
new file mode 100644
index 0000000..4dcd682
--- /dev/null
+++ b/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/savePlayerData.java
@@ -0,0 +1,227 @@
+package com.slprojects.slcraftplugin.tachesParalleles;
+
+import com.slprojects.slcraftplugin.Main;
+import org.bukkit.ChatColor;
+import org.bukkit.Statistic;
+import org.bukkit.entity.Player;
+
+import java.sql.Connection;
+import java.sql.PreparedStatement;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.time.Duration;
+import java.time.LocalDateTime;
+import java.time.ZoneOffset;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.UUID;
+
+public class savePlayerData {
+    private final Main plugin;
+    private Connection con;
+    // Playtime
+    private final List<UUID> playTimeUsersIndexes;
+    private final List<LocalDateTime> playTimeUsersDate;
+
+    public savePlayerData(Main plugin){
+        this.plugin = plugin;
+        playTimeUsersIndexes = new ArrayList<>();
+        playTimeUsersDate = new ArrayList<>();
+    }
+
+    public void saveOnJoin(Player player) {
+        // On ouvre la bdd
+        con = plugin.bddOpenConn();
+
+        playTimeUsersIndexes.add(player.getUniqueId());
+        playTimeUsersDate.add(LocalDateTime.now());
+
+        insertPlayerName(player); // On check si le nom du joueur est déjà enregistré
+        playerAddPlayerEntryOrExit(player, true); // On ajoute son entée
+        checkJoinedDate(player); // On check si on dipose de sa date de rejoint
+        setPlayerJoinCount(player); // On set le nombre de fois qu'il a rejoint
+
+        // On ferme la bdd
+        try {
+            con.close();
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Impossible de fermer la connexion à la bdd. Func savePlayerData::saveOnJoin(Player player)");
+            e.printStackTrace();
+        }
+    }
+
+    public void saveOnQuit(Player player) {
+        // On ouvre la bdd
+        con = plugin.bddOpenConn();
+
+        calculatePlayerPlayTime(player); // On actualise le temps de jeu du joueur
+        playerAddPlayerEntryOrExit(player, false); // On ajoute son sortie
+
+        // On ferme la bdd
+        try {
+            con.close();
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Impossible de fermer la connexion à la bdd. Func savePlayerData::saveOnQuit(Player player)");
+            e.printStackTrace();
+        }
+    }
+
+    // Fonctions
+    private void insertPlayerName(Player player){
+        try {
+            // On va d'abord regarder si on a déjà renseigné le nom du joueur
+            PreparedStatement rechercheUtilisateur = con.prepareStatement("SELECT * FROM site_userSetting WHERE uuid = ? AND name = 'playerName' AND value = ?");
+            rechercheUtilisateur.setString(1, player.getUniqueId().toString());
+            rechercheUtilisateur.setString(2, player.getName());
+            ResultSet resultat = rechercheUtilisateur.executeQuery();
+
+            if(resultat.next()){
+                // On a déjà renseigné le nom du joueur on va donc vérifier s'il a besoin d'être mis à jour
+                if(!resultat.getString("value").equals(player.getName())){
+                    // On va mettre à jour le nom du joueur
+                    PreparedStatement updateUtilisateur = con.prepareStatement("UPDATE site_userSetting SET value = ? WHERE uuid = ? AND name = 'playerName'");
+                    updateUtilisateur.setString(1, player.getName());
+                    updateUtilisateur.setString(2, player.getUniqueId().toString());
+                    updateUtilisateur.executeUpdate();
+                }
+            }else{
+                // On peut insérer le nom du joueur
+                PreparedStatement insertUtilisateur = con.prepareStatement("INSERT INTO site_userSetting (uuid, name, value) VALUES (?, 'playerName', ?)");
+                insertUtilisateur.setString(1, player.getUniqueId().toString());
+                insertUtilisateur.setString(2, player.getName());
+                insertUtilisateur.executeQuery();
+            }
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Func savePlayerData::insertPlayerName(Player player)");
+            e.printStackTrace();
+        }
+    }
+
+    private void playerAddPlayerEntryOrExit(Player player, boolean isEnter){
+        try {
+            PreparedStatement insertPlayerEntryOrExit = con.prepareStatement("INSERT INTO site_playerEntries (uuid, isJoin, date) VALUES (?, ?, ?)");
+            insertPlayerEntryOrExit.setString(1, player.getUniqueId().toString());
+            insertPlayerEntryOrExit.setBoolean(2, isEnter);
+            insertPlayerEntryOrExit.setString(3, java.sql.Timestamp.valueOf(java.time.LocalDateTime.now()).toString());
+            insertPlayerEntryOrExit.executeQuery();
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Func savePlayerData::playerAddPlayerEntryOrExit(Player player, boolean isEnter)");
+            e.printStackTrace();
+        }
+    }
+
+    private void checkJoinedDate(Player player){
+        try {
+            // On va vérifier si on l'a déjà renseigné par le passé
+            PreparedStatement rechercheUtilisateur = con.prepareStatement("SELECT * FROM site_userSetting WHERE uuid = ? AND name = 'joinedDate'");
+            rechercheUtilisateur.setString(1, player.getUniqueId().toString());
+            ResultSet resultat = rechercheUtilisateur.executeQuery();
+
+            if(!resultat.next()){
+                // On n'a pas renseigné la date de création du joueur
+                if(player.hasPlayedBefore()){
+                    // On va piocher la date d'inscription chez CoreProtect (si elle existe)
+                    // On la prend chez CoreProtect car le plugin a été installé dans les premières semaines du serveur. Il a donc bcp plus de données que nous concernant les anciens joueurs.
+                    PreparedStatement rechercheDateInscription = con.prepareStatement("SELECT time FROM co_user WHERE uuid = ?");
+                    rechercheDateInscription.setString(1, player.getUniqueId().toString());
+                    resultat = rechercheDateInscription.executeQuery();
+
+                    if(resultat.next()){
+                        // On insère la date d'inscription
+                        PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
+                        insertionDateInscription.setString(1, player.getUniqueId().toString());
+                        insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(LocalDateTime.ofEpochSecond(Long.parseLong(resultat.getString("time")), 0, ZoneOffset.UTC)).toString()); // Il faut convertir le timestamp (epoch second) en date
+                        insertionDateInscription.executeQuery();
+
+                        // On va précisier que la date d'inscription a été trouvée chez CoreProtect
+                        plugin.getLogger().info("Le joueur "+ ChatColor.GOLD+player.getName()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs. On lui a donc attribué comme date de création du compte, celle que détenait CoreProtect.");
+                    } else {
+                        // On insère la date d'inscription (du coup on considère que Le joueur n'a pas joué avant, malgré la condition)
+                        PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
+                        insertionDateInscription.setString(1, player.getUniqueId().toString());
+                        insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(java.time.LocalDateTime.now()).toString());
+                        insertionDateInscription.executeQuery();
+
+                        // On va préciser que la date d'inscription n'a pas été trouvée chez CoreProtect
+                        PreparedStatement insertionInaccurrateJoinedDate = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'inaccurrateJoinedDate',?)");
+                        insertionInaccurrateJoinedDate.setString(1, player.getUniqueId().toString());
+                        insertionInaccurrateJoinedDate.setString(2, "true");
+                        insertionInaccurrateJoinedDate.executeQuery();
+
+                        // On est daccord que ceci n'est pas censé arriver, cela ne concerne que mes potes n'étant venus que durant les premières semaines du serveur.
+
+                        plugin.getLogger().info("Le joueur "+ChatColor.GOLD+player.getName()+ChatColor.RESET+" n'avait pas de données sur sa date d'inscription dans dans la table des paramètres utilisateurs, ni dans la table des utilisateurs de CoreProtect. On lui a donc attribué comme date de création du compte, la date du début de sa partie.");
+                    }
+                }else{
+                    // Le joueur est nouveau, on insère la date d'inscription
+                    PreparedStatement insertionDateInscription = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joinedDate',?)");
+                    insertionDateInscription.setString(1, player.getUniqueId().toString());
+                    insertionDateInscription.setString(2, java.sql.Timestamp.valueOf(java.time.LocalDateTime.now()).toString());
+                    insertionDateInscription.executeQuery();
+                }
+            }
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Func savePlayerData::checkJoinedDate(Player player)");
+            e.printStackTrace();
+        }
+    }
+
+    void setPlayerJoinCount(Player player){
+        try{
+            // On va vérifier si on a déjà renseigné le nombre de fois que le joueur a rejoint le serveur par le passé
+            PreparedStatement rechercheJoinCount = con.prepareStatement("SELECT * FROM site_userSetting WHERE uuid = ? AND name = 'joins'");
+            rechercheJoinCount.setString(1, player.getUniqueId().toString());
+            ResultSet resultat = rechercheJoinCount.executeQuery();
+
+            if(resultat.next()){
+                // On a déjà renseigné ça par le passé, on va donc faire un update
+                PreparedStatement updateJoinCount = con.prepareStatement("UPDATE site_userSetting SET value = ? WHERE uuid = ? AND name = 'joins'");
+                updateJoinCount.setString(1, String.valueOf(player.getStatistic(Statistic.LEAVE_GAME) + 1));
+                updateJoinCount.setString(2, player.getUniqueId().toString());
+                updateJoinCount.executeQuery();
+            }else{
+                // On n'a pas encore renseigné le nombre de fois que le joueur a rejoint le serveur, on va donc faire un insert
+                PreparedStatement insertionJoinCount = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'joins',?)");
+                insertionJoinCount.setString(1, player.getUniqueId().toString());
+                insertionJoinCount.setString(2, String.valueOf(player.getStatistic(Statistic.LEAVE_GAME) + 1));
+                insertionJoinCount.executeQuery();
+            }
+
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Func savePlayerData::setPlayerJoinCount(Player player)");
+            e.printStackTrace();
+        }
+    }
+
+    private void calculatePlayerPlayTime(Player player){
+        // On va calculer le temps de jeu du joueur
+        LocalDateTime timeNow = LocalDateTime.now();
+        Duration duration = Duration.between(timeNow, playTimeUsersDate.get(playTimeUsersIndexes.indexOf(player.getUniqueId())));
+        long playedTimeInSeconds = Math.abs(duration.toSeconds());
+
+        try{
+            // On va vérifier si on a déjà renseigné le temps de jeu du joueur par le passé
+            PreparedStatement recherchePlayTime = con.prepareStatement("SELECT * FROM site_userSetting WHERE uuid = ? AND name = 'playedTime'");
+            recherchePlayTime.setString(1, player.getUniqueId().toString());
+            ResultSet resultat = recherchePlayTime.executeQuery();
+
+            if(resultat.next()){
+                // On a déjà renseigné ça par le passé, on va donc faire un update
+                PreparedStatement updatePlayTime = con.prepareStatement("UPDATE site_userSetting SET value = ? WHERE uuid = ? AND name = 'playedTime'");
+                updatePlayTime.setString(1, String.valueOf(Long.parseLong(resultat.getString("value")) + playedTimeInSeconds));
+                updatePlayTime.setString(2, player.getUniqueId().toString());
+                updatePlayTime.executeQuery();
+            }else{
+                // On n'a pas encore renseigné le temps de jeu du joueur, on va donc faire un insert
+                PreparedStatement insertionPlayTime = con.prepareStatement("INSERT INTO site_userSetting (`uuid`, `name`, `value`) VALUES (?,'playedTime',?)");
+                insertionPlayTime.setString(1, player.getUniqueId().toString());
+                insertionPlayTime.setString(2, String.valueOf(playedTimeInSeconds));
+                insertionPlayTime.executeQuery();
+            }
+
+        } catch (SQLException e) {
+            plugin.getLogger().warning(ChatColor.RED + "Func savePlayerData::increasePlayerPlayTime(Player player)");
+            e.printStackTrace();
+        }
+    }
+}
diff --git a/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/waitForDiscordMsg.java b/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/waitForDiscordMsg.java
index 432d5ca..f2e15bc 100644
--- a/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/waitForDiscordMsg.java
+++ b/src/main/java/com/slprojects/slcraftplugin/tachesParalleles/waitForDiscordMsg.java
@@ -74,8 +74,9 @@ public class waitForDiscordMsg {
 
                                         // On envoie le message aux joueurs
                                         for(Player p : plugin.getServer().getOnlinePlayers()){
-                                            p.sendMessage(ChatColor.DARK_PURPLE + playerName + " : " + ChatColor.WHITE + message);
+                                            p.sendMessage(ChatColor.DARK_PURPLE + playerName + ChatColor.WHITE + ": " + message);
                                         }
+                                        plugin.getLogger().info(ChatColor.DARK_PURPLE + playerName + ": " + message);
                                         out.print("Message envoyé !");
                                         break;
                                     default:
diff --git a/src/main/resources/config.yml b/src/main/resources/config.yml
index 4d1dd37..827723a 100644
--- a/src/main/resources/config.yml
+++ b/src/main/resources/config.yml
@@ -28,4 +28,4 @@ player-join-message: "&a%player_name% &fa rejoint le serveur :D"
 player-quit-message: "&a%player_name% &fvient de quitter le serveur :'("
 
 # Serveur messagerie
-msg-server-port: 25566
\ No newline at end of file
+msg-server-port: 25575
\ No newline at end of file
diff --git a/target/classes/com/slprojects/slcraftplugin/Main.class b/target/classes/com/slprojects/slcraftplugin/Main.class
index 7b8b54cb644d050ba3e31aa80c3f5e8263644ffd..7986bf8f35deeba66e788eadeffc166b28a7a87f 100644
GIT binary patch
delta 4757
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

literal 17345
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

diff --git a/target/classes/config.yml b/target/classes/config.yml
index 4d1dd37..827723a 100644
--- a/target/classes/config.yml
+++ b/target/classes/config.yml
@@ -28,4 +28,4 @@ player-join-message: "&a%player_name% &fa rejoint le serveur :D"
 player-quit-message: "&a%player_name% &fvient de quitter le serveur :'("
 
 # Serveur messagerie
-msg-server-port: 25566
\ No newline at end of file
+msg-server-port: 25575
\ No newline at end of file
diff --git a/target/classes/plugin.yml b/target/classes/plugin.yml
index a3f955e..057d35f 100644
--- a/target/classes/plugin.yml
+++ b/target/classes/plugin.yml
@@ -1,5 +1,5 @@
 name: SLCraftPlugin
-version: '1.5'
+version: '1.5.1'
 main: com.slprojects.slcraftplugin.Main
 depend: [PlaceholderAPI]
 api-version: 1.18
diff --git a/target/maven-archiver/pom.properties b/target/maven-archiver/pom.properties
index c717738..df790c8 100644
--- a/target/maven-archiver/pom.properties
+++ b/target/maven-archiver/pom.properties
@@ -1,5 +1,5 @@
 #Generated by Maven
-#Sun Mar 06 22:53:05 CET 2022
+#Mon Mar 07 20:27:25 CET 2022
 groupId=com.slprojects
 artifactId=SLCraftPlugin
-version=1.5
+version=1.5.1
-- 
GitLab