Skip to content
Snippets Groups Projects
Select Git revision
  • bb17a163f0b3bbd78e3c5b9279555d8fecec02d9
  • main default protected
  • feature/revoir_gestion_bdd
  • 1.6.1
  • 1.6.0
5 results

InternalWebServer.java

Blame
  • Main.java 21.44 KiB
    // Contient une partie du code de ce plugin: https://github.com/Twi5TeD/PlayTime
    
    package com.slprojects.slcraftplugin;
    
    import com.slprojects.slcraftplugin.commandes.linkCodeCommand;
    import com.slprojects.slcraftplugin.commandes.wildCommand;
    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;
    import org.bukkit.event.EventPriority;
    import org.bukkit.event.Listener;
    import org.bukkit.event.player.AsyncPlayerChatEvent;
    import org.bukkit.event.player.PlayerJoinEvent;
    import org.bukkit.event.player.PlayerQuitEvent;
    import org.bukkit.plugin.java.JavaPlugin;
    import org.json.simple.JSONObject;
    import org.mariadb.jdbc.MariaDbPoolDataSource;
    
    import java.io.BufferedReader;
    import java.io.InputStreamReader;
    import java.io.UnsupportedEncodingException;
    import java.net.HttpURLConnection;
    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;
    
        // Fonctions appelées à des évènements clés
        @Override
        public void onEnable() {
            // On s'assure qu'on a placeholder api
            if (getServer().getPluginManager().getPlugin("PlaceholderAPI") != null) {
                getLogger().info("PlaceholderAPI chargé");
                // On initialise les listeners
                getServer().getPluginManager().registerEvents(this, this);
            } else {
                getLogger().info(ChatColor.RED+"PlaceholderAPI n'est pas accessible!");
                getServer().getPluginManager().disablePlugin(this);
            }
    
            // Plugin startup logic
            saveDefaultConfig();
            reloadConfig();
            config = getConfig();
    
            // 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);
    
            linkCodeCommand linkCodeCommand = new linkCodeCommand(this);
            getCommand("getLinkCode").setExecutor(linkCodeCommand);
    
            waitForDiscordMsg.startServer(this);
    
            getLogger().info(ChatColor.GREEN+"SL-Craft | Plugin démarré");
        }
    
        @Override
        public void onDisable() {
            // Plugin shutdown logic
            getLogger().info(ChatColor.RED+"SL-Craft | Plugin éteint");
    
            getServer().getOnlinePlayers().forEach(this::savePlayer);
        }
    
        @EventHandler(priority = EventPriority.HIGHEST)
        public void onPlayerJoin(PlayerJoinEvent e) {
            playTimeUsersIndexes.add(e.getPlayer().getUniqueId());
            playTimeUsersDate.add(LocalDateTime.now());
    
            // On affiche le message de bienvenue
            String welcomeMessage = PlaceholderAPI.setPlaceholders(e.getPlayer(), getConfig().getString("player-join-message"));
            // Et on joue un petit son chez tous les joueurs
            for(Player p : getServer().getOnlinePlayers()){
                p.sendMessage(welcomeMessage);
                if(getConfig().getBoolean("player-join-playSound")){
                    p.playSound(p.getLocation(), Sound.ENTITY_EXPERIENCE_ORB_PICKUP, 1, 0);
                }
                //p.sendMessage(welcomeMessage);
            }
        }
    
        @EventHandler(priority = EventPriority.HIGHEST)
        public void onPlayerQuit(PlayerQuitEvent e) {
            savePlayer(e.getPlayer());
            String quitMessage = PlaceholderAPI.setPlaceholders(e.getPlayer(), getConfig().getString("player-quit-message"));
            for(Player p : getServer().getOnlinePlayers()){
                p.sendMessage(quitMessage);
            }
        }
    
        // On renvoie chaque message des joueurs sur le canal de chat du serveur discord
        @SuppressWarnings("unchecked")
        @EventHandler(priority = EventPriority.LOWEST)
        void AsyncChatEvent(AsyncPlayerChatEvent e) throws UnsupportedEncodingException {
            // On va appeler l'api du bot discord
            JSONObject json = new JSONObject();
            json.put("message", e.getMessage());
            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);
                HttpURLConnection con = (HttpURLConnection) url.openConnection();
                con.setRequestMethod("GET");
                con.setRequestProperty("User-Agent", "Mozilla/5.0");
                con.setRequestProperty("Accept-Language", "en-US,en;q=0.5");
                con.setRequestProperty("Content-Type", "application/json");
                con.setDoOutput(true);
                con.setDoInput(true);
                con.setUseCaches(false);
                con.setAllowUserInteraction(false);
                con.setConnectTimeout(5000);
                con.setReadTimeout(5000);
                con.connect();
                BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
                String inputLine;
                StringBuilder response = new StringBuilder();
                while ((inputLine = in.readLine()) != null) {
                    response.append(inputLine);
                }
                in.close();
                con.disconnect();
                getLogger().info(response.toString());
            } catch (Exception ex) {
                ex.printStackTrace();
            }
        }
    
        // 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)){
                return false;
            }else{
                wildCommandActiveUsers.add(playerUuid);
                return true;
            }
        }
        public void removeActiveUserForWildCommand(UUID playerUuid){
            if(wildCommandActiveUsers.contains(playerUuid)){
                try {
                    TimeUnit.SECONDS.sleep(5);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                wildCommandActiveUsers.remove(playerUuid);
            }
        }
    
        public Connection bddOpenConn() { // si mot de passe avec des caractère spéciaux
            Connection conn=null;
            try {
                Class.forName("org.mariadb.jdbc.MariaDbPoolDataSource");
            } catch (ClassNotFoundException e){
                getLogger().warning (ChatColor.RED+"Il manque le driver MariaDB!");
                getServer().getPluginManager().disablePlugin(this);
            }
            try {
                MariaDbPoolDataSource dataSource = new MariaDbPoolDataSource("jdbc:mariadb://"+config.getString("database.host")+"/"+config.getString("database.database")+"?user="+config.getString("database.user")+"&password="+config.getString("database.password")+"&maxPoolSize=10");
                conn = dataSource.getConnection();
                //getLogger().info(ChatColor.GREEN+"Connexion à la base de données réussie!");
            }// ou les saisir
            catch (SQLException e) {
                getLogger().warning(ChatColor.RED+"Erreur lors de la connexion à la base de données.");
                getServer().getPluginManager().disablePlugin(this);
            }
            return conn;
        }
    
        private void initDatabase(){
            try{
                Connection con = bddOpenConn();
                PreparedStatement ps=con.prepareStatement("CREATE TABLE IF NOT EXISTS `site_userSetting` (\n" +
                        "  `uuid` varchar(36) NOT NULL DEFAULT '',\n" +
                        "  `name` varchar(128) NOT NULL,\n" +
                        "  `value` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,\n" +
                        "  PRIMARY KEY (`uuid`,`name`) USING BTREE\n" +
                        ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;");
                ps.executeQuery();
                ps=con.prepareStatement("CREATE TABLE IF NOT EXISTS `site_linkCode` (\n" +
                        " `uuid` VARCHAR(36) NOT NULL,\n" +
                        " `code` VARCHAR(8) NOT NULL,\n" +
                        " `time` TIMESTAMP NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp(),\n" +
                        " `used` BOOLEAN,\n" +
                        " PRIMARY KEY (`uuid`),\n" +
                        " UNIQUE INDEX `code` (`code`)\n" +
                        ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;");
                ps.executeQuery();
                con.close();
            }catch(Exception e){
                getLogger().warning(ChatColor.RED+"Erreur lors de l'exécution de initDatabase(): "+e);
            }
        }
    
        // API Spring
        /*
        @GetMapping("/discordMsg/{jsonEncodedString}")
        void sendDiscordMessage(){
    
        }*/
    }