Nouvelle version de Juliabot - début du code

This commit is contained in:
Mysaa 2021-05-23 01:31:56 +02:00
parent 5124a36c7a
commit 53262acf09
31 changed files with 759 additions and 1727 deletions

0
build.gradle Normal file
View File

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.2 KiB

0
settings.gradle Normal file
View File

View File

@ -1,306 +0,0 @@
package com.bernard.discord;
import java.util.*;
import com.bernard.discord.api.Command;
import com.bernard.discord.api.DUtils;
import com.bernard.discord.struct.CommandMap;
import net.dv8tion.jda.core.*;
import net.dv8tion.jda.core.entities.*;
public class DiscordBot {
// private static DiscordBot julia;
private JDA jda;
private CommandMap commandMap;
private Scanner sc;
public boolean running;
public short countDown;
private com.bernard.discord.struct.EventListener listener;
private String[] changelog = {
// "Patch 20180309 :",
// "L'arr<72>t automatique ne se d<>clenche plus apr<70>s un
// StatusChangeEvent.",
// "Le message d'arr<72>t automatique ne s'envoie plus qu'une fois dans
// chaque channel.",
// "Une certaine commande changelog aurai <20>t<EFBFBD> ajout<75>, est-ce la
// v<EFBFBD>rit<EFBFBD> ?"
// "Patch 20180330 :", "Le jeu de JuL'IA change selon si elle est en
// mode fant<EFBFBD>me ou non.",
// "La commande julia a <20>t<EFBFBD> am<61>lior<6F>, mais des r<>glages sur les
// proba sont encore <EFBFBD> faire",
// "Les logs enl<6E>vent enfin les tags utilisateurs et salons, au
// revoir les notifs doublons !!!"};
"Patch 20180403 :", "Nouvelle commande modif, qui permet de ... modifier",
"Les possibilit<69>s offertes par les commandes dlc et sayc sont maintenant prises en charge par dl et say",
"Les commandes sont indiqu<71>es et de nombreux autres events ont un nom plus court dans les logs"};
public static void main(String[] args) {
new DiscordBot("!!", "");
// new DiscordBot("::",
// "NDM5ODU2MjY3ODc2NjMwNTQ4.DcZQDg.2gV5E-JUMeWYhpVBTLuhtfEJNEo");
}
public DiscordBot(String tag, String token) {
try {
jda = new JDABuilder(AccountType.BOT)/*
* .setStatus(OnlineStatus.
* INVISIBLE)
*/.setToken(token).buildBlocking();
Thread.sleep(2000);
} catch(Exception e) {
e.printStackTrace();
}
// jda.getPresence().setGame(Game.playing("r<EFBFBD>unir toutes les donn<6E>es,
// les donn<EFBFBD>es"));
DUtils.init(jda, tag);
// jda.getPresence().setGame(Game.playing("trier les events"));
listener = new com.bernard.discord.struct.EventListener(this);
// jda.getPresence().setGame(Game.playing("trier les commandes"));
commandMap = new CommandMap(this, tag, listener);
DUtils.loadMaps(commandMap, listener);
// String time = DUtils.getTime();
// String mess = "----- " + time + " Connexion -----";
// DUtils.logS.sendMessage(mess).complete();
// DUtils.logE.sendMessage(mess).complete();
// DUtils.logV.sendMessage(mess).complete();
sc = new Scanner(System.in);
running = true;
countDown = 0;
jda.addEventListener(listener);
// jda.getPresence().setGame(Game.listening("TOUT depuis " + time));
run();
}
public void run() {
System.out.println("[" + DUtils.getTime() + "] [Info] [ZLO]: Scanner ready!\n");
while(running)
if(sc.hasNextLine())
commandMap.commandConsole(sc.nextLine());
}
private final String URG = "";
@Command(name = "stop", group = "Contr<EFBFBD>le", grp = "ctr", description = "Met fin <20> l'ex<65>cution du bot", admin = true)
public void stop() {
running = false;
stop(URG);
}
public void stop(String message) {
// String time = DUtils.getTime();
// boolean urg = message == URG;
// if(urg)
// jda.getPresence().setGame(Game.listening("RIEN depuis " + time));
// String tmessage = "----- " + time + " Arr<72>t " + (urg ? "manuel" :
// ("automatique --- " + message)) + " -----";
// DUtils.logS.sendMessage(tmessage).complete();
// DUtils.logE.sendMessage(tmessage).complete();
// DUtils.logV.sendMessage(tmessage).complete();
jda.shutdownNow();
System.exit(0);
}
// @Command(name = "changelog", group = "Contr<EFBFBD>le", grp = "ctr", description
// = "Donne des informations utiles sur la version de l'instance lanc<6E>e.",
// admin = true)
// public void changelog(TextChannel channel) throws InterruptedException {
// sendWithDelay(channel, changelog);
// }
public static void sendWithDelay(MessageChannel channel, String... messages) {
try {
for(String message : messages) {
channel.sendTyping().complete();
Thread.sleep(message.length() * 75);
channel.sendMessage(message).complete();
}
} catch(InterruptedException e) {
e.printStackTrace();
}
}
/**
* Kick Members 1 2 Add Reactions 6 64 View Audit Logs 7 128 Read Text
* Channels & See Voice Channels 10 1024 Read Messages 10 1024 Send Messages
* 11 2048 Send TTS Messages 12 4096 Manage Messages 13 8192 Embed Links 14
* 16384 Attach Files 15 32768 Read History 16 65536 Mention Everyone 17
* 131072 Use External Emojis 18 262144 Connect 20 1048576 Speak 21 2097152
* Mute Members 22 4194304 Deafen Members 23 8388608 Move Members 24
* 16777216 Use Voice Activity 25 33554432 Change Nickname 26 67108864
* Manage Roles 28 268435456 Manage Permissions 28 268435456 Manage Webhooks
* 29 536870912 Manage Emojis 30 1073741824
*/
// @Command(name = "tts", group = "Contr<EFBFBD>le", grp = "ctr", description =
// "Oula... faut pas que tu lise <20>a hein, c'est dangereux hein. ET
// TECHNIQUEMENT IMPOSSIBLE. Mais <EFBFBD>a c'est pas important.", admin = true)
// public void test(User user, Member member, MessageChannel channel, Guild
// guild, String[] args) throws InterruptedException {
//// if(member.getUser().getIdLong() != 232545563407548416L)
//// return;
//
//
//
// MessageBuilder mb = new MessageBuilder();
// mb.setTTS(true);
// for(String arg : args)
// mb.append(arg).append(" ");
// Message m = mb.build();
//// guild.getController().setNickname(guild.getSelfMember(),
// "MEE6").complete();
//// guild.getTextChannelById(222947179017404416L).sendMessage(m).complete().delete().complete();
// guild.getController().setNickname(guild.getSelfMember(),
// "JuL'IA").complete();
// }
// @Command(name = "pool", group = "Contr<EFBFBD>le", grp = "ctr", description =
// "Oula... faut pas que tu lise <20>a hein, c'est dangereux hein. ET
// TECHNIQUEMENT IMPOSSIBLE. Mais <EFBFBD>a c'est pas important.", admin = false)
// public void pool(Member member, MessageChannel channel, Guild guild,
// String[] args) throws InterruptedException {
// if(member.getUser().getIdLong() != 232545563407548416L) {
// String message = "Zone dangeureuse, travaux en cours.";
// channel.sendTyping().complete();
// channel.sendMessage(message).completeAfter(message.length() * 75,
// TimeUnit.MILLISECONDS).delete().completeAfter(message.length() * 225,
// TimeUnit.MILLISECONDS);
// return;
// }
//
// StringBuilder s = new StringBuilder();
// for(AuditLogEntry entry : guild.getAuditLogs())
// s.append(entry.getUser().getName()).append(" ");
// channel.sendMessage(s.toString()).complete();
//
// }
// boolean top = false;
//
// @Command(name = "loop", group = "Contr<EFBFBD>le", grp = "ctr", description =
// "Oula... faut pas que tu lise <20>a hein, c'est dangereux hein. ET
// TECHNIQUEMENT IMPOSSIBLE. Mais <EFBFBD>a c'est pas important.", admin = false)
// public void loop(Member member, MessageChannel channel, Guild guild,
// String[] args) throws InterruptedException {
// if(member.getUser().getIdLong() != 232545563407548416L) {
// String message = "Zone dangeureuse, travaux en cours.";
// channel.sendTyping().complete();
// channel.sendMessage(message).completeAfter(message.length() * 75,
// TimeUnit.MILLISECONDS).delete().completeAfter(message.length() * 225,
// TimeUnit.MILLISECONDS);
// return;
// }
// top = true;
//
//
// Member m = guild.getMemberById(187677269626585089L);
//
// VoiceChannel v1 = guild.getVoiceChannelById(356199104357072907L);
// VoiceChannel v2 = guild.getVoiceChannelById(358622259918798859L);
// while(top) {
// Thread.sleep(250);
// guild.getController().moveVoiceMember(m, v1).queue();
// Thread.sleep(250);
// guild.getController().moveVoiceMember(m, v2).complete();
// }
//
// }
//
// @Command(name = "truth", group = "Contr<EFBFBD>le", grp = "ctr", description =
// "Oula... faut pas que tu lise <20>a hein, c'est dangereux hein. ET
// TECHNIQUEMENT IMPOSSIBLE. Mais <EFBFBD>a c'est pas important.", admin = false)
// public void truth(Member member, MessageChannel channel, Guild guild,
// String[] args) throws InterruptedException {
// top = false;
// }
//
// @Command(name = "zulu", group = "Contr<EFBFBD>le", grp = "ctr", description =
// "Oula... faut pas que tu lise <20>a hein, c'est dangereux hein. ET
// TECHNIQUEMENT IMPOSSIBLE. Mais <EFBFBD>a c'est pas important.", admin = false)
// public void zulu(Member member, MessageChannel channel, Guild guild,
// String[] args) throws InterruptedException {
// if(member.getUser().getIdLong() != 232545563407548416L)
// return;
// for(Category ca : guild.getCategories()) {
// System.out.println(ca.getName());
// for(Channel c : ca.getChannels()) {
// System.out.println("\t" + c.getName());
// for(Member m : c.getMembers()) {
// System.out.println("\t\t" + m.getEffectiveName());
// }
// }
// }
// }
//
// public void test1(User user, MessageChannel channel, Guild guild,
// String[] args) throws InterruptedException {
// if(user.getIdLong() != 232545563407548416L) {
// String message = "Zone dangeureuse, travaux en cours.";
// channel.sendTyping().complete();
// channel.sendMessage(message).completeAfter(message.length() * 75,
// TimeUnit.MILLISECONDS).delete().completeAfter(message.length() * 225,
// TimeUnit.MILLISECONDS);
// return;
// }
// List<Message> rh = channel.getHistoryBefore(args[0],
// Integer.parseInt(args[1])).complete().getRetrievedHistory();
// StringBuilder sb = new StringBuilder("```\n");
//
// for(Message m : rh)
// m.delete().complete();
// // try {
// // for(int i = 0; i < rh.size(); i++) {
// // System.out.println(i);
// // String m = rh.get(i).getId()+" :
// // "+rh.get(i).getContent().replaceAll("```", "'''").replaceAll("\n", "
// // \\\\n ")+"\n";
// // if(sb.length()+m.length() > 1997) {
// // channel.sendMessage(sb.append("```").toString()).complete();
// // sb.setLength(0);
// // sb.append("```\n");
// // } sb.append(m);
// // }channel.sendMessage(sb.append("```").toString()).complete();
// // } catch (IllegalArgumentException e) {
// // System.out.println(sb.toString());
// // }
// }
@Command(name = "dllasts", group = "Contr<EFBFBD>le", grp = "ctr", description = "", admin = true)
public void dllast(MessageChannel channel, User user, String[] args) {
if(user.getIdLong() != 232545563407548416L)
return;
List<Message> l = channel.getIterableHistory().complete();
int first = 0;
for(int i = 0; i < l.size(); i++)
if(l.get(i).getId().equals(args[0])) {
first = i;
break;
}
for(int i = first; i < l.size() && i < first + Integer.parseInt(args[1]); i++) {
try {
Message m = l.get(i);
m.delete().complete();
Thread.sleep(400);
} catch(Exception e) {
e.printStackTrace();
}
}
}
}

View File

@ -1,168 +0,0 @@
package com.bernard.discord.addons;
import java.util.List;
import com.bernard.discord.api.Command;
import com.bernard.discord.api.DUtils;
import net.dv8tion.jda.client.managers.EmoteManager;
import net.dv8tion.jda.core.entities.*;
import net.dv8tion.jda.core.requests.Route.Emotes;
public class Basics {
// ----- POUVOIR ----- \\
// @Command(name = "modif", group = "Contrôle", grp = "ctr", description = "Modifie un message", admin = true)
// public void modif(String[] args, TextChannel thisChannel) {
// boolean cVersion = false;
// TextChannel channel = null;
//
// try {
// channel = DUtils.server.getTextChannelById(args[0]);
// channel.toString();
// } catch(Exception e) {
// if(channel == null) {
// channel = thisChannel;
// cVersion = true;
// }
// }
//
// StringBuilder sb = new StringBuilder();
// for(int i = cVersion ? 1 : 2; i < args.length; i++)
// sb.append(args[i] + " ");
// String message = sb.toString();
//
// channel.getMessageById(args[cVersion ? 0 : 1]).complete().editMessage(message).complete();
// }
//
// @Command(name = "say", group = "Contrôle", grp = "ctr", description = "Envoie un message", admin = true)
// public void say(String[] args, TextChannel thisChannel) {
// boolean cVersion = false;
// TextChannel channel = null;
// try {
// channel = DUtils.server.getTextChannelById(args[0]);
// channel.toString();
// } catch(Exception e) {
// if(channel == null) {
// channel = thisChannel;
// cVersion = true;
// }
// }
//
// StringBuilder sb = new StringBuilder();
// for(int i = cVersion ? 0 : 1; i < args.length; i++)
// sb.append(args[i] + " ");
// String message = sb.toString();
//
// DiscordBot.sendWithDelay(channel, message);
// }
//
// @Command(name = "dl", group = "Contrôle", grp = "ctr", description = "Efface un message", admin = true)
// public void dl(String[] args, TextChannel thisChannel) {
// boolean cVersion = false;
// TextChannel channel = null;
// try {
// channel = DUtils.server.getTextChannelById(args[0]);
// channel.toString();
// } catch(Exception e) {
// if(channel == null) {
// channel = thisChannel;
// cVersion = true;
// }
// }
//
// channel.getMessageById(args[cVersion ? 0 : 1]).complete().delete().complete();
// }
@Command(name = "rea", group = "Contrôle", grp = "ctr", description = "Ajoute une réaction", admin = true)
public void rea(String[] args, Guild guild, MessageChannel thischan, Message message) {
// List<Emote> emotes = guild.getEmotes();
//
// for(Emote emote : emotes)
// System.out.println(emote.getId()+" : "+emote.getName());
boolean cVersion = false;
MessageChannel channel = null;
try {
channel = DUtils.server.getTextChannelById(args[0]);
channel.toString();
} catch(Exception e) {
if(channel == null) {
channel = thischan;
cVersion = true;
}
}
// for(char c : message.getContent().toCharArray())
// System.out.println(c + " : " + (int)c);
// int[] wow = new int[]{55358,56614,55357,56489,55356,57185,55356,57246,55357,56446,55357,56875,55357,56495,55357,56396,55357,56697,55356,57241,11093,55357,56601,55357,56604,55357,56865};
// StringBuilder sb = new StringBuilder();
// for(int i = 0; i < wow.length/2; i++)
// sb.append((char)wow[2*i]).append("+").append((char)wow[2*i+1]).append("=").append((char)wow[2*i]).append((char)wow[2*i+1]).append("\n");
// channel.sendMessage(sb.toString()).complete();
// channel.getMessageById(args[cVersion ? 0 : 1]).complete().addReaction(guild.getEmotesByName(args[cVersion ? 1 : 2], true).get(0)).complete();
// channel.getMessageById(args[cVersion ? 0 : 1]).complete().addReaction(message.getEmotes().get(0)).complete();
}
@Command(name = "inttochar", group = "", grp = "", description = "", admin = true)
public void inttochar(String[] args, Guild guild, MessageChannel chan, Message message) {
String[] ints = message.getContent().split("!!inttochar ")[1].split(", ");
StringBuilder sb = new StringBuilder();
inttocharParser(sb, ints[0]);
for(int i = 1; i < ints.length; i++){
sb.append(", ");
inttocharParser(sb, ints[i]);
}
chan.sendMessage(sb.toString()).complete();
}
private void inttocharParser(StringBuilder sb, String s) {
sb.append(s).append(" = ");
if(s.contains("..")) {
int from = Integer.parseInt(s.split("\\.\\.")[0]);
int to = Integer.parseInt(s.split("\\.\\.")[1]);
int step = from < to ? 1 : -1;
sb.append("{").append((char)from);
for(int j = from+step; j < to; j+=step)
sb.append(", ").append((char)j);
sb.append("}");
}else
sb.append((char)Integer.parseInt(s));
}
// ----- ETAT ----- \\
// @Command(name = "show", group = "Contrôle", grp = "ctr", description = "Inverse le status en ligne du bot", admin = true)
// public void show(JDA jda) {
// Presence wow = jda.getPresence();
// if(wow.getStatus() == OnlineStatus.INVISIBLE)
// wow.setStatus(OnlineStatus.ONLINE);
// else
// wow.setStatus(OnlineStatus.INVISIBLE);
// }
//
// @Command(name = "game", group = "Contrôle", grp = "ctr", description = "Change le jeu courant", admin = true)
// public void game(JDA jda, String[] args) {
// StringBuilder sb = new StringBuilder();
// for(String arg : args)
// sb.append(arg).append(" ");
// jda.getPresence().setGame(Game.playing(sb.toString()));
// }
//
// @Command(name = "julia", group = "Contrôle", grp = "ctr", description = "Répond à l'appel", admin = true)
// public void julia(MessageChannel channel, User user) {
// String[] julias = new String[]{"Présent !", "Présente !", "Présentbleu !", "Présentavion !", "Présent(e) !", "Présent(bleu) !",
// "Présent(avion) !", "Présent(e)(bleu) !", "Présent(e)(avion) !", "Présent(bleu)(avion) !", "Présent(e)(bleu)(avion) !",
// "Oui, c'est moi", user.getName(), "ailuJ", "42 ... oups", "C'est à moi que tu parle ?!", "Entrez c'est ouvert", "Derrière toi !!!",
// "J'ai tujorous pas cropmis a qoui ca sret l'otrahhgrope ...", "Laissez moi préparer la domination du monde en paix s'il vous plaît !",
// "Je SuIS Un RObot BZzzBzZZZbZZbZZ", "Juliaaaa dadedidadeda dedadedi dadeda", "Tutturu", "Tadaaaaaaa !"};
// String[] out = new String[]{julias[(int)Math.floor(Math.random() * julias.length)]};
//
// DiscordBot.sendWithDelay(channel, out);
// }
}

View File

@ -1,126 +0,0 @@
package com.bernard.discord.addons;
public class Lists {
// @Command(name = "roleColor", group = "Liste", grp = "lst", description = "Composante de la couleur d'un role, a partir d'une mention de ce role, ou d'un membre ayant ce role comme principal", admin = true)
// public void roleColor(Guild guild, MessageChannel channel, Message message) {
// List<Role> roles = message.getMentionedRoles();
// if(roles.size() == 0) {
// List<User> users = message.getMentionedUsers();
// if(users.size() == 0)
// return;
// roles = guild.getMember(users.get(0)).getRoles();
// if(roles.size() == 0)
// System.out.println("AAAAAAA");
// }
// Role role = roles.get(0);
// Color color = role.getColor();
//
// float[] hsb = Color.RGBtoHSB(color.getRed(), color.getGreen(), color.getBlue(), (float[])null);
//
// EmbedBuilder builder = new EmbedBuilder();
// builder.setTitle("Color of " + role.getName());
// builder.setColor(color);
//
// builder.addField("", "", false);
// builder.addField(":closed_book:Red", "" + color.getRed(), true);
// builder.addField(":green_book:Green", "" + color.getGreen(), true);
// builder.addField(":blue_book:Blue", "" + color.getBlue(), true);
//
// builder.addField("", "", false);
// builder.addField(":rainbow:Hue", "" + hsb[0] * 360, true);
// builder.addField(":performing_arts:Saturation", "" + hsb[1], true);
// builder.addField(":flashlight:Brightness", "" + hsb[2], true);
//
// channel.sendMessage(builder.build()).complete();
// }
//
// @Command(name = "users", group = "Liste", grp = "lst", description = "Liste les membres suivant leur id", admin = true)
// public void users(Guild guild, MessageChannel channel) {
// EmbedBuilder builder = new EmbedBuilder();
// List<Member> ms = guild.getMembers(), members = new ArrayList<Member>(ms);
//
// members.sort(new MemberByIDComparator());
// builder.setTitle("Liste des membres du serveur");
//
// StringBuilder sb = new StringBuilder();
// for(int i = 0; i < members.size(); i++)
// sb.append(members.get(i).getUser().getId() + " \"" + members.get(i).getEffectiveName() + "\"\n");
//
// builder.addField("", sb.toString(), true);
// builder.setColor(DUtils.color);
//
// channel.sendMessage(builder.build()).complete();
// }
//
// @Command(name = "rolesID", group = "Liste", grp = "lst", description = "Liste les rôles suivant leur ID", admin = true)
// public void rolesID(Guild guild, MessageChannel channel) {
// EmbedBuilder builder = new EmbedBuilder();
// List<Role> ms = guild.getRoles(), roles = new ArrayList<Role>(ms);
//
// roles.sort(new RolesByIDComparator());
// builder.setTitle("Liste des rôles du serveur");
//
// StringBuilder sb = new StringBuilder();
// for(int i = 0; i < roles.size(); i++) {
// String roleName = roles.get(i).getName();
// sb.append(roles.get(i).getIdLong() + " \"" + (roleName.startsWith("@") ? "everyone" : roleName) + "\"\n");
// }
//
// builder.addField("", sb.toString(), true);
// builder.setColor(DUtils.color);
//
// channel.sendMessage(builder.build()).complete();
// }
//
// @Command(name = "rolesRank", group = "Liste", grp = "lst", description = "Liste les rôles suivant leur rang", admin = true)
// public void rolesRank(Guild guild, MessageChannel channel) {
// EmbedBuilder builder = new EmbedBuilder();
// List<Role> ms = guild.getRoles(), roles = new ArrayList<Role>(ms);
//
// roles.sort(new RolesByRankComparator());
// builder.setTitle("Liste des rôles du serveur");
//
// StringBuilder sb = new StringBuilder();
// for(int i = 0; i < roles.size(); i++) {
// String roleName = roles.get(i).getName();
// sb.append(roles.get(i).getPosition() + " \"" + (roleName.startsWith("@") ? "everyone" : roleName) + "\"\n");
// }
//
// builder.addField("", sb.toString(), true);
// builder.setColor(DUtils.color);
//
// channel.sendMessage(builder.build()).complete();
// }
//
// public class MemberByIDComparator implements Comparator<Member> {
//
// public int compare(Member o1, Member o2) {
// if(o1.getUser().getIdLong() > o2.getUser().getIdLong())
// return 1;
// return -1;
// }
//
// }
//
// public class RolesByIDComparator implements Comparator<Role> {
//
// public int compare(Role o1, Role o2) {
// if(o1.getIdLong() > o2.getIdLong())
// return 1;
// return -1;
// }
//
// }
//
// public class RolesByRankComparator implements Comparator<Role> {
//
// public int compare(Role o1, Role o2) {
// if(o1.getPosition() > o2.getPosition())
// return 1;
// return -1;
// }
//
// }
//
}

View File

@ -1,170 +0,0 @@
package com.bernard.discord.addons;
import com.bernard.discord.api.DUtils;
public class Logs {
// public long previousEventID;
//
// @Discord(description = "Détecte un message serveur pour le mettre dans les logs")
// public void guildReceived(GuildMessageReceivedEvent event) {
// String eventName;
// if(EventListener.commandIDs.contains(event.getMessage().getIdLong())) {
// eventName = "CommandReceived";
// int index = EventListener.commandIDs.indexOf(event.getMessageIdLong());
// EventListener.commandIDs.remove(index);
// } else
// eventName = "MessageReceived";
//
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, eventName);
// load(s, "user", event.getAuthor().getName());
// load(s, "chan", event.getChannel().getName());
// load(s, "mess", event.getMessage().getContent());
// sendE(s);
// }
//
// @Discord(description = "Détecte la modification d'un message serveur pour le mettre dans les logs")
// public void guildUpdate(GuildMessageUpdateEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "MessageUpdate");
// load(s, "user", event.getAuthor().getName());
// load(s, "chan", event.getChannel().getName());
// load(s, "mess", event.getMessage().getContent());
// sendE(s);
// }
//
// @Discord(description = "Détecte la supression d'un message serveur pour le mettre dans les logs")
// public void guildDelete(GuildMessageDeleteEvent event) {
//
// if(EventListener.deleteIDs.contains(event.getMessageIdLong())) {
// int index = EventListener.deleteIDs.indexOf(event.getMessageIdLong());
// EventListener.deleteIDs.remove(index);
// return;
// }
//
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "MessageDelete");
// load(s, "chan", event.getChannel().getName());
// sendE(s);
// }
//
// @Discord(description = "Détecte une arrivée dans un salon vocal pour le mettre dans les logs")
// public void voiceJoin(GuildVoiceJoinEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "GuildVoiceJoin");
// load(s, "user", event.getMember().getUser().getName());
// load(s, "chan", event.getChannelJoined().getName());
// sendV(s);
// }
//
// @Discord(description = "Détecte un changement de salon vocal pour le mettre dans les logs")
// public void voiceMove(GuildVoiceMoveEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "VocalMove");
// load(s, "user", event.getMember().getUser().getName());
// load(s, "left", event.getChannelLeft().getName());
// load(s, "join", event.getChannelJoined().getName());
// sendV(s);
// }
//
// @Discord(description = "Détecte un départ de salon vocal pour le mettre dans les logs")
// public void voiceLeave(GuildVoiceLeaveEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "VocalLeave");
// load(s, "user", event.getMember().getUser().getName());
// load(s, "chan", event.getChannelLeft().getName());
// sendV(s);
// }
//
// @Discord(description = "Détecte un changement de status pour le mettre dans les logs")
// public void statusUpdate(UserOnlineStatusUpdateEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "StatusUpdate");
// load(s, "user", event.getUser().getName());
// load(s, "old", event.getPreviousOnlineStatus());
// load(s, "new", event.getGuild().getMember(event.getUser()).getOnlineStatus());
// sendS(s);
// }
//
// @Discord(description = "Détecte un changement de jeu pour le mettre dans les logs")
// public void gameUpdate(UserGameUpdateEvent event) {
// StringBuilder s = new StringBuilder();
// load(s, DUtils.getTime());
// load(s, event.getResponseNumber());
// load(s, "GameUpdate");
// load(s, "user", event.getUser().getName());
//
// Game old = event.getPreviousGame();
// if(old != null)
// load(s, "old", old.getName());
//
// Game nev = event.getGuild().getMember(event.getUser()).getGame();
// if(nev != null)
// load(s, "new", nev.getName());
//
// sendS(s);
// }
private void load(StringBuilder s, Object value) {
if(s.length() != 0)
separ(s);
if(value != null)
s.append(value);
else
s.append("null");
}
private void load(StringBuilder s, String name, Object value) {
if(s.length() != 0)
separ(s);
s.append(name).append("=");
if(value != null)
s.append(value);
else
s.append("null");
}
private void separ(StringBuilder s) {
s.append(", ");
}
private void sendE(StringBuilder s) {
if(s.length() > 1950) {
int length = s.length();
s.setLength(1950);
s.append("...\"");
load(s, "length", length);
}
DUtils.logE.sendMessage(s.toString()).queue();
System.out.println(s.toString());
s.setLength(0);
}
private void sendV(StringBuilder s) {
DUtils.logV.sendMessage(s.toString()).queue();
System.out.println(s.toString());
s.setLength(0);
}
private void sendS(StringBuilder s) {
DUtils.logS.sendMessage(s.toString()).queue();
System.out.println(s.toString());
s.setLength(0);
}
}

View File

@ -1,157 +0,0 @@
package com.bernard.discord.addons;
import java.util.ArrayList;
import java.util.Stack;
import com.bernard.discord.api.Command;
import com.bernard.meganumber.arithmetic.MegaN;
import com.bernard.meganumber.arithmetic.RadixConversion;
import net.dv8tion.jda.core.entities.MessageChannel;
public class MegaNumber {
private static RadixConversion converter = new RadixConversion();
@Command(name = "calct", group = "MegaNumber", grp = "mn", description = "Comprends un calcul et en fournit le résultat. Elements actuellement compris :\n"
+ "\t- Sommes et produits explicites\n" + "\t- Entiers naturels en développement décimal propre\n"
+ "\t- Système de parenthésages corrects", admin = false)
public void calct(MessageChannel channel, String[] args) {
try {
String su = args[0];
for(int i = 1; i < args.length; i++)
su += " " + args[i];
String s = su.replaceAll("\\(", " ( ");
s = s.replaceAll("\\)", " ) ");
s = s.replaceAll("\\*", " * ");
s = s.replaceAll("\\+", " + ");
s = s.replaceAll("\\^", " ^ ");
String ss = "";
while(!ss.equals(s)) {
ss = s;
s = s.replaceAll(" ", " ");
}
String[] tokens = s.split(" ");
ArrayList<String> liste = new ArrayList<String>();
for(int i = 0; i < tokens.length; i++)
liste.add(tokens[i]);
Stack<String> operator = new Stack<String>();
Stack<Object> out = new Stack<Object>();
boolean prio = false;
for(int i = 0; i < liste.size(); i++) {
String token = liste.get(i);
if(!operator.isEmpty()) {
if("+".equals(token) && "*".equals(operator.peek()) || "*".equals(token) && "^".equals(operator.peek()) || "+".equals(token)
&& "^".equals(operator.peek())) {
out.push(operator.pop());
operator.push(token);
prio = true;
}
}
if(!prio)
try {
MegaN n = new MegaN(token);
out.push(n);
} catch(NumberFormatException nfe) {
if(")".equals(token)) {
while(!"(".equals(operator.peek()))
out.push(operator.pop());
operator.pop();
} else
operator.push(token);
}
prio = false;
}
while(operator.isEmpty() == false)
if(")".equals(operator.peek()) || "(".equals(operator.peek()))
operator.pop();
else
out.push(operator.pop());
Stack<Object> out2 = new Stack<Object>();
while(out.size() > 0)
out2.push(out.pop());
Stack<MegaN> out3 = new Stack<MegaN>();
while(out2.size() > 0)
if(out2.peek() instanceof MegaN)
out3.push((MegaN)out2.pop());
else {
String ope = "" + out2.pop();
if(ope.equals("+")) {
MegaN n2 = out3.pop();
MegaN n1 = out3.pop();
MegaN n3 = MegaN.add(n1, n2);
// System.out.println(n1+" + "+n2+" = "+n3);
out3.push(n3);
} else if(ope.equals("*")) {
MegaN n2 = out3.pop();
MegaN n1 = out3.pop();
MegaN n3 = MegaN.mul(n1, n2);
// System.out.println(n1+" * "+n2+" = "+n3);
out3.push(n3);
} else if(ope.equals("^")) {
MegaN n2 = out3.pop();
MegaN n1 = out3.pop();
MegaN n3 = MegaN.pow(n1, n2);
// System.out.println(n1+" ^ "+n2+" = "+n3);
out3.push(n3);
}
}
channel.sendMessage(su.replaceAll("\\*", "\\\\*") + " = " + out3.peek().toString()).complete();
} catch(Exception e) {
System.err.println("calc");
e.printStackTrace();
}
}
// @Command(name = "add", group = "MegaNumber", grp = "mn", description = "Additionne les entiers en arguments", admin = false)
// public void add(String[] args, MessageChannel channel) {
// MegaN[] ns = new MegaN[args.length];
// ns[0] = new MegaN(args[0]);
// StringBuilder sb = new StringBuilder(args[0]);
// for(int i = 1; i < args.length; i++) {
// sb.append(" + ").append(args[i]);
// ns[i] = new MegaN(args[i]);
// }
// channel.sendMessage(sb.append(" = ").append(MegaN.add(ns)).toString()).complete();
// }
//
// @Command(name = "mul", group = "MegaNumber", grp = "mn", description = "Multiplie les entiers en arguments", admin = false)
// public void mul(String[] args, MessageChannel channel) {
// MegaN[] ns = new MegaN[args.length];
// ns[0] = new MegaN(args[0]);
// StringBuilder sb = new StringBuilder(args[0]);
// for(int i = 1; i < args.length; i++) {
// sb.append(" * ").append(args[i]);
// ns[i] = new MegaN(args[i]);
// }
// channel.sendMessage(sb.append(" # ").append(MegaN.mul(ns)).toString()).complete();
// }
@Command(name = "pow", group = "MegaNumber", grp = "mn", description = "Renvoie le résultat du deuxième entier mis en exposant du premier", admin = false)
public void pow(String[] args, MessageChannel channel) {
channel.sendMessage(new StringBuilder(args[0]).append(" ^ ").append(args[1]).append(" = ").append(MegaN.pow(new MegaN(args[0]), new MegaN(
args[1]))).toString()).complete();
}
// @Command(name = "10to2", group = "MegaNumber", grp = "mn", description = "Convertit l'argument décimal en binaire", admin = false)
// public void dTOb(String[] args, MessageChannel channel) {
// String binaire = converter.decimalToBinary(args[0]);
// channel.sendMessage("0d" + args[0] + " -> 0b" + binaire).complete();
// }
//
// @Command(name = "2to10", group = "MegaNumber", grp = "mn", description = "Convertit l'argument binaire en décimal", admin = false)
// public void bTOd(String[] args, MessageChannel channel) {
// String decimal = converter.binaryToDecimal(args[0]);
// channel.sendMessage("0b" + args[0] + " -> 0d" + decimal).complete();
// }
}

View File

@ -1,48 +0,0 @@
package com.bernard.discord.addons;
import com.bernard.discord.DiscordBot;
import com.bernard.discord.api.DUtils;
import com.bernard.discord.api.Discord;
import net.dv8tion.jda.core.OnlineStatus;
import net.dv8tion.jda.core.entities.*;
import net.dv8tion.jda.core.events.message.MessageReceivedEvent;
import net.dv8tion.jda.core.events.message.guild.GuildMessageReceivedEvent;
import net.dv8tion.jda.core.events.user.UserOnlineStatusUpdateEvent;
public class Rigolos {
@Discord(description = "Réagi à l'apparition d'un Samy")
public void pouet(UserOnlineStatusUpdateEvent event) {
if(event.getUser().getIdLong() == 229320114321752075L) { // Samy
Guild guild = event.getGuild();
Member m = guild.getMemberById(232545563407548416L); // Moua
User u = m.getUser();
PrivateChannel pc = u.openPrivateChannel().complete();
String psn = event.getPreviousOnlineStatus().name();
String asn = guild.getMember(event.getUser()).getOnlineStatus().name();
pc.sendMessage(psn + " -> " + asn).complete();
}
}
@Discord(description = "Répond \"pouet\" à tout les messages de Christine")
public void pouet(GuildMessageReceivedEvent event) {
if(event.getAuthor().getIdLong() == 321977394565087235L) // Christine
DiscordBot.sendWithDelay(event.getChannel(), "pouet");
}
@Discord(description = "Envoie \"*Dieu arrive*\" quand Yukimyo se connecte")
public void dieu(UserOnlineStatusUpdateEvent event) {
if(event.getUser().getIdLong() == 187677269626585089L) // Arthur
if(event.getPreviousOnlineStatus() == OnlineStatus.OFFLINE)
DiscordBot.sendWithDelay(DUtils.ppublique, "*Dieu arrive*");
}
@Discord(description = "Réagi à l'apparition d'un \"wow\"")
public void wow(MessageReceivedEvent event) {
if(event.getAuthor().getIdLong() != 359788121795198977L) // JuLIA
if(event.getMessage().getContent().contains("wow"))
event.getChannel().sendMessage("wow").complete();
}
}

View File

@ -1,111 +0,0 @@
package com.bernard.discord.addons;
import java.util.*;
import com.bernard.discord.api.Command;
import com.bernard.discord.api.Discord;
import net.dv8tion.jda.core.EmbedBuilder;
import net.dv8tion.jda.core.entities.*;
import net.dv8tion.jda.core.events.message.react.MessageReactionAddEvent;
public class Votes {
@Discord(description = "")
public void addReac(MessageReactionAddEvent e, MessageChannel chan) {
System.out.println(e.getReaction().toString());
Vote v = Vote.getByQuestionID(e.getMessageIdLong());
if(v == null)
return;
MessageReaction r = e.getReaction();
System.out.println(e.getReactionEmote().getName());
// long emoteID =
// if(!v.emoteIDs.contains(emoteID))
// return;
// v.userEmoteIDs.put(e.getUser().getIdLong(), emoteID);
r.removeReaction(e.getUser()).complete();
v.refreshResult();
}
@Command(name = "newPoll", group = "", grp = "", description = "", admin = true)
public void newPoll(MessageChannel chan, Message m, Guild g) {
// Message r = chan.sendMessage(" - ").complete();
String[] args = m.getContent().split("!!newPoll")[1].split(",");
String[] emotes = new String[args.length/2];
int emoteCount = 0;
String[] descrs = new String[args.length/2];
int descrCount = 0;
for(String arg : args) {
arg = arg.trim();
if(arg.contains("\"")) {
System.out.println("oui"+arg.replace("\"", ""));
emotes[emoteCount++] = arg.replace("\"", "");
} else {
System.out.println("non"+arg);
descrs[descrCount++] = arg;
}
}
EmbedBuilder e = new EmbedBuilder();
for(int i = 0; i < emotes.length; i++) {
System.out.println("\""+descrs[i] + "\" et \""+emotes[i]+"\"");
e.addField(descrs[i], emotes[i], true);
}
Message q = chan.sendMessage(e.build()).complete();
for(int i = 0; i < emotes.length; i++) {
q.rea
q.addReaction(emotes[i]).complete();
}
// MessageReaction.ReactionEmote emote = reaction.getReactionEmote();
//
// return emote.isEmote()
// ? emote.getName() + ":" + emote.getId()
// : MiscUtil.encodeUTF8(emote.getName());
// new Vote(q.getIdLong(), r, emoteIDs);
}
public static class Vote {
static ArrayList<Vote> votes = new ArrayList<Vote>();
Map<Long, Long> userEmoteIDs = new HashMap<Long, Long>();
List<Long> emoteIDs;
long questionID;
Message result;
public Vote(long questionID_, Message result_, List<Long> emoteIDs_) {
votes.add(this);
emoteIDs = emoteIDs_;
questionID = questionID_;
result = result_;
}
public void refreshResult() {
EmbedBuilder e = new EmbedBuilder();
for(long emoteID : emoteIDs) {
int count = 0;
for(long userEmoteID : userEmoteIDs.values())
if(userEmoteID == emoteID)
count++;
e.addField("" + 471290594732408832L, "" + count, false);
}
result.editMessage(e.build());
}
public static Vote getByQuestionID(long questionID) {
for(Vote v : votes)
if(v.questionID == questionID)
return v;
return null;
}
}
}

View File

@ -1,29 +0,0 @@
package com.bernard.discord.addons;
import com.bernard.discord.api.Command;
import net.dv8tion.jda.core.Permission;
import net.dv8tion.jda.core.entities.*;
public class Wow {
// @Command(name = "chan", group = "", grp = "", description = "", admin = true)
// public void chan(MessageChannel chan) {
// OffsetDateTime wow = chan.getCreationTime();
// chan.sendMessage(wow.getYear()+"/"+wow.getMonthValue()+"/"+wow.getDayOfMonth()).complete().delete().queueAfter(15, TimeUnit.SECONDS);
// }
//
@Command(name = "admin", group = "", grp = "", description = "", admin = true)
public void admin(Member m, Guild g) {
Role r = g.getRolesByName("Dieu discret", false).get(0);
if(!m.getRoles().contains(r))
return;
if(r.hasPermission(Permission.ADMINISTRATOR))
r.getManager().revokePermissions(Permission.ADMINISTRATOR);
else
r.getManager().givePermissions(Permission.ADMINISTRATOR);
}
}

View File

@ -1,86 +0,0 @@
package com.bernard.discord.api;
import java.awt.Color;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import org.reflections.Reflections;
import org.reflections.scanners.MethodAnnotationsScanner;
import com.bernard.discord.struct.CommandMap;
import net.dv8tion.jda.core.JDA;
import net.dv8tion.jda.core.entities.*;
public class DUtils {
public static CommandMap commands;
public static com.bernard.discord.struct.EventListener events;
public static Color color = new Color(113, 82, 182);;
public static String tag;
public static JDA jda;
public static Guild server;
public static TextChannel logS;
public static TextChannel logE;
public static TextChannel logV;
public static TextChannel test;
public static TextChannel juliadmin;
public static TextChannel ppublique;
public static Role matrixWriter;
public static Reflections reflections;
public static void init(JDA jdap, String tagp) {
tag = tagp;
jda = jdap;
server = jda.getGuildById(222947179017404416L);
logS = server.getTextChannelById(361480293682774047L);
logE = server.getTextChannelById(281843607168745473L);
logV = server.getTextChannelById(361505020815867904L);
test = server.getTextChannelById(278296310891937792L);
juliadmin = server.getTextChannelById(395637091364634625L);
matrixWriter = server.getRoleById(402574932132757534L);
ppublique = server.getTextChannelById(222947179017404416L);
reflections = new Reflections(".*", new MethodAnnotationsScanner());
}
public static void loadMaps(CommandMap commandsp, com.bernard.discord.struct.EventListener eventsp) {
commands = commandsp;
events = eventsp;
}
public static String getTime() {
Locale locale = new Locale("FR", "fr");
Calendar calendar = Calendar.getInstance(locale);
Date date = calendar.getTime();
DateFormat fFormat = new SimpleDateFormat("HH:mm:ss");
DateFormat dFormat = new SimpleDateFormat("E");
String fDate = "", fHeur = "";
fHeur = fFormat.format(date);
fDate = dayFromFR(dFormat.format(date)) + " ";
return fDate + fHeur;
}
private static String dayFromFR(String fr) {
switch(fr) {
case "lun.":
return "Mon";
case "mar.":
return "Tue";
case "mer.":
return "Wed";
case "jeu.":
return "Thu";
case "ven.":
return "Fri";
case "sam.":
return "Sat";
case "dim.":
return "Sun";
default:
return fr;
}
}
}

View File

@ -1,243 +0,0 @@
package com.bernard.discord.struct;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.*;
import java.util.Map.Entry;
import org.reflections.Reflections;
import com.bernard.discord.DiscordBot;
import com.bernard.discord.api.Command;
import com.bernard.discord.api.DUtils;
import net.dv8tion.jda.core.JDA;
import net.dv8tion.jda.core.entities.*;
public final class CommandMap {
private final Map<String, CommandObject> commands;
private final Map<Class, Object> objects;
String tag;
public CommandMap(DiscordBot bot, String tag, EventListener listener) {
System.out.println("[" + DUtils.getTime() + "] [Info] [ZLO]: Command map is being created");
objects = new HashMap<>();
commands = new HashMap<>();
this.tag = tag;
objects.put(getClass(), this);
objects.put(listener.getClass(), listener);
objects.put(bot.getClass(), bot);
addCommands();
StringBuilder sb = new StringBuilder();
for(Entry entry : commands.entrySet())
sb.append(entry.getKey()).append(" ");
System.out.println("[" + DUtils.getTime() + "] [Info] [ZLO]: Command map has been created with " + commands.size() + " commands :\n\t" + sb
.toString() + "\n");
}
private void addCommands() {
Reflections reflections = DUtils.reflections;
Set<Method> methods = reflections.getMethodsAnnotatedWith(Command.class);
for(Method method : methods) {
if(method.isAnnotationPresent(Command.class)) {
boolean error = false;
try {
Class clazz = method.getDeclaringClass();
Command command = method.getAnnotation(Command.class);
method.setAccessible(true);
CommandObject simpleCommand = null;
if(!objects.containsKey(clazz))
try {
objects.put(clazz, clazz.newInstance());
} catch(InstantiationException | IllegalAccessException e1) {
e1.printStackTrace();
}
Object object = objects.get(clazz);
try {
simpleCommand = new CommandObject(command.name(), command.description(), command.group(), command.grp(), command.admin(),
object, method);
} catch(Exception e) {
e.printStackTrace();
}
commands.put(simpleCommand.getName(), simpleCommand);
} catch(Exception e) {
error = true;
System.err.println("\n" + e.getClass().getSimpleName() + " while loading " + method.getDeclaringClass().getName() + "." + method
.getName() + "() : ");
e.printStackTrace();
System.err.println();
}
if(!error)
System.out.println("\t" + method.getDeclaringClass().getSimpleName() + "." + method.getName()
+ "() have been successfully loaded");
}
}
System.out.println();
}
public void commandConsole(String command) {
Object[] object = getCommand(command);
if(object[0] == null) {
try{
throw new IllegalArgumentException("La methode \"" + command + "\" n'existe pas ");
}catch(Exception e) {
e.printStackTrace();
}
return;
}
new Thread("Console Command Thread") {
public void run() {
try {
execute(((CommandObject)object[0]), command, (String[])object[1], null);
} catch(Exception e) {
e.printStackTrace();
}
}
}.start();
}
public boolean commandUser(Member member, Message message, Guild guild) {
String command = message.getContent();
if(!command.startsWith(tag))
return false;
EventListener.commandIDs.add(message.getIdLong());
EventListener.deleteIDs.add(message.getIdLong());
String command2 = command.replaceFirst(tag, "");
Object[] object = getCommand(command2);
if(object[0] == null)
return false;
if(((CommandObject)object[0]).isAdmin() && !member.getRoles().contains(DUtils.matrixWriter))
return false;
new Thread("User Command Thread") {
public void run() {
try {
execute(((CommandObject)object[0]), command2, (String[])object[1], message);
} catch(Exception e) {
e.printStackTrace();
}
}
}.start();
return true;
}
private Object[] getCommand(String command) {
String[] commandSplit = command.split(" ");
String[] args = new String[commandSplit.length - 1];
for(int i = 1; i < commandSplit.length; i++)
args[i - 1] = commandSplit[i];
CommandObject simpleCommand = commands.get(commandSplit[0]);
return new Object[]{simpleCommand, args};
}
private void execute(CommandObject simpleCommand, String command, String[] args, Message message) throws Exception {
Parameter[] parameters = simpleCommand.getMethod().getParameters();
Object[] objects = new Object[parameters.length];
for(int i = 0; i < parameters.length; i++) {
if(parameters[i].getType() == String[].class)
objects[i] = args;
else if(parameters[i].getType() == User.class)
objects[i] = message == null ? null : message.getAuthor();
else if(parameters[i].getType() == Member.class)
objects[i] = message == null ? null : DUtils.server.getMember(message.getAuthor());
else if(parameters[i].getType() == TextChannel.class)
objects[i] = message == null ? null : message.getTextChannel();
else if(parameters[i].getType() == PrivateChannel.class)
objects[i] = message == null ? null : message.getPrivateChannel();
else if(parameters[i].getType() == Guild.class)
objects[i] = message == null ? null : DUtils.server;
else if(parameters[i].getType() == String.class)
objects[i] = command;
else if(parameters[i].getType() == Message.class)
objects[i] = message;
else if(parameters[i].getType() == JDA.class)
objects[i] = DUtils.jda;
else if(parameters[i].getType() == MessageChannel.class)
objects[i] = message == null ? null : message.getChannel();
else if(parameters[i].getType() == TextChannel[].class)
objects[i] = new TextChannel[]{DUtils.logS, DUtils.logE, DUtils.logV};
// System.out.println("objects["+i+"] prend la valeur "+objects[i]);
}
simpleCommand.getMethod().invoke(simpleCommand.getObject(), objects);
}
// @Command(name = "help", group = "Help", grp = "hlp", description = "Affiche la liste des commandes existantes", admin = false)
// public void help(Member member, Guild guild, MessageChannel channel, String[] args) {
// ArrayList<String> groups = new ArrayList<String>();
// ArrayList<String> grps = new ArrayList<String>();
// for(CommandObject command : commands.values())
// if(!groups.contains(command.getGroup())) {
// groups.add(command.getGroup());
// grps.add(command.getGrp());
// }
//
// String[] groupss = new String[groups.size()];
// String[] grpss = new String[groups.size()];
// for(int i = 0; i < groupss.length; i++) {
// groupss[i] = groups.get(i);
// grpss[i] = grps.get(i);
// }
//
// User user = member.getUser();
// if(!user.hasPrivateChannel())
// user.openPrivateChannel().complete();
//
// EmbedBuilder eB = new EmbedBuilder();
// eB.setColor(DUtils.color);
//
// boolean isGrp = args.length > 0;
// if(isGrp)
// isGrp = grps.contains(args[0]);
// boolean isGroup = args.length > 0;
// if(isGroup)
// isGroup = groups.contains(args[0]);
//
// if(isGroup || isGrp) {
// String grp = isGrp ? args[0] : grps.get(groups.indexOf(args[0]));
// String group = isGroup ? args[0] : groups.get(grps.indexOf(args[0]));
// eB.setTitle("Liste des commandes du groupe " + group + " ( " + grp + ")");
// for(CommandObject command : commands.values()) {
// if(command.getGroup().equals(group))
// if(!command.isAdmin() || member.getRoles().contains(DUtils.matrixWriter))
// eB.addField(command.getName(), command.getDescription(), false);
// }
// } else {
// eB.setTitle("Liste des groupes de commande");
//
// boolean[] hasCommand = new boolean[groupss.length];
// for(int i = 0; i < groupss.length; i++)
// hasCommand[i] = false;
//
// for(CommandObject command : commands.values())
// if(!command.isAdmin() || member.getRoles().contains(DUtils.matrixWriter))
// hasCommand[groups.indexOf(command.getGroup())] |= true;
// for(int i = 0; i < groups.size(); i++) {
// if(hasCommand[i]) {
// String group = groupss[i];
// String grp = grpss[i];
// StringBuilder commandsList = new StringBuilder();
// for(CommandObject command : commands.values()) {
// if(command.getGroup().equals(group)) {
// if(!command.isAdmin() || member.getRoles().contains(DUtils.matrixWriter))
// commandsList.append(command.getName()).append(", ");
// }
// }
// eB.addField(group + " ( " + grp + " )", commandsList.toString(), false);
// }
// }
// }
// // channel.sendMessage(eB.build()).complete();
// ((UserImpl)user).getPrivateChannel().sendMessage(eB.build()).queue();
// }
}

View File

@ -1,51 +0,0 @@
package com.bernard.discord.struct;
import java.lang.reflect.Method;
public class CommandObject {
private final String group, grp, name, description;
private final boolean admin;
private final Object object;
private final Method method;
public CommandObject(String name, String desc, String group, String grp, boolean admin, Object object, Method method) {
// this.fullName = (group.equals("")?"":(group+":")) + name;
this.name = name;
this.group = group;
this.grp = grp;
this.description = desc;
this.admin = admin;
this.object = object;
this.method = method;
}
public String getGrp() {
return grp;
}
public String getName() {
return name;
}
public String getGroup() {
return group;
}
public String getDescription() {
return description;
}
public boolean isAdmin() {
return admin;
}
public Object getObject() {
return object;
}
public Method getMethod() {
return method;
}
}

View File

@ -1,193 +0,0 @@
package com.bernard.discord.struct;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import org.reflections.Reflections;
import com.bernard.discord.DiscordBot;
import com.bernard.discord.api.DUtils;
import com.bernard.discord.api.Discord;
import net.dv8tion.jda.core.events.Event;
import net.dv8tion.jda.core.events.ReconnectedEvent;
import net.dv8tion.jda.core.events.message.MessageReceivedEvent;
import net.dv8tion.jda.core.events.message.guild.GuildMessageReceivedEvent;
import net.dv8tion.jda.core.events.message.priv.PrivateMessageReceivedEvent;
public class EventListener implements net.dv8tion.jda.core.hooks.EventListener {
private final DiscordBot bot;
private final Map<String, EventObject> events;
private final Map<Class, Object> objects;
// private final Logs log = new Logs();
public static ArrayList<Long> commandIDs = new ArrayList<Long>();
public static ArrayList<Long> deleteIDs = new ArrayList<Long>();
private boolean waitPrivate = false, waitGuild = false;
private int eventCount = 0;
private long lastEventID = -10;
private String lastEventType = "null";
public EventListener(DiscordBot bot) {
System.out.println("[" + DUtils.getTime() + "] [Info] [ZLO]: Event listener is being created");
objects = new HashMap<>();
events = new HashMap<>();
objects.put(getClass(), this);
objects.put(bot.getClass(), bot);
addEvents();
this.bot = bot;
System.out.println("[" + DUtils.getTime() + "] [Info] [ZLO]: Event listener has been created with " + events.size() + " events\n");
}
public void onEvent(Event event) {
try{
if(!bot.running)
if(bot.countDown++ == 5)
return;
if(event.getResponseNumber() > 0) {
if(event.getResponseNumber() < lastEventID) {
if(!(event instanceof ReconnectedEvent)) {
bot.running = false;
bot.stop(lastEventType + "(" + lastEventID + ") ->" + event.getClass().getSimpleName() + "(" + event.getResponseNumber() + ")");
}
}
lastEventID = event.getResponseNumber();
lastEventType = event.getClass().getSimpleName();
}
if(event instanceof MessageReceivedEvent)
return;
if(event instanceof GuildMessageReceivedEvent) {
GuildMessageReceivedEvent event2 = (GuildMessageReceivedEvent)event;
if(event2.getChannel().getName().startsWith("logs"))
return;
if(DUtils.commands.commandUser(DUtils.server.getMember(event2.getAuthor()), event2.getMessage(), DUtils.server))
event2.getMessage().delete().complete();
}
if(event instanceof PrivateMessageReceivedEvent) {
PrivateMessageReceivedEvent event2 = (PrivateMessageReceivedEvent)event;
DUtils.commands.commandUser(DUtils.server.getMember(event2.getAuthor()), event2.getMessage(), DUtils.server);
}
ArrayList<EventObject> eventsConcerned = new ArrayList<EventObject>();
for(Entry<String, EventObject> entry : events.entrySet())
if(entry.getKey().startsWith(event.getClass().getSimpleName()))
eventsConcerned.add(entry.getValue());
for(EventObject object : eventsConcerned)
new Thread("User Event Thread") {
public void run() {
try {
execute(object, event);
} catch(Exception e) {
e.printStackTrace();
}
}
}.start();
// log.previousEventID = event.getResponseNumber();
}catch(Exception e) {
System.err.println("listener");
e.printStackTrace();
}
}
private void addEvents() {
Reflections reflections = DUtils.reflections;
Set<Method> methods = reflections.getMethodsAnnotatedWith(Discord.class);
label: for(Method method : methods) {
if(method.isAnnotationPresent(Discord.class)) {
boolean error = false;
try {
Class<?> clazz = method.getDeclaringClass();
Discord event = method.getAnnotation(Discord.class);
method.setAccessible(true);
EventObject simpleEvent = null;
if(!objects.containsKey(clazz))
try {
objects.put(clazz, clazz.newInstance());
} catch(InstantiationException | IllegalAccessException e1) {
e1.printStackTrace();
}
Object object = objects.get(clazz);
try {
int i = 0;
for(Class<?> p : method.getParameterTypes())
if(Event.class.isAssignableFrom(p))
i++;
if(i > 1) {
System.err.println(clazz.getSimpleName() + " : " + method.getName());
System.err.println(i + " events en m<>me temps... La simultan<61>it<69> est relative, non ?");
continue label;
}
if(i == 0) {
System.err.println("");
System.err.println("Pas d'event en argument ! Tu fait tout <20>a pour surveiller... rien ?!");
continue label;
}
Class clu = null;
for(Class p : method.getParameterTypes())
if(Event.class.isAssignableFrom(p))
clu = p;
simpleEvent = new EventObject(clu, object, event.description(), method);
} catch(Exception e) {
e.printStackTrace();
}
events.put(simpleEvent.getClazz().getSimpleName() + eventCount++, simpleEvent);
} catch(Exception e) {
error = true;
System.err.println("\n" + e.getClass().getSimpleName() + " while loading " + method
.getDeclaringClass().getName() + "." + method.getName()+"() : ");
e.printStackTrace();
System.err.println();
}
if(!error)
System.out.println("\t" + method.getDeclaringClass().getSimpleName() + "." + method.getName() + "() have been successfully loaded");
}
}
}
private void execute(EventObject simpleEvent, Event event) throws Exception {
// PrintStream
Parameter[] parameters = simpleEvent.getMethod().getParameters();
Object[] objects = new Object[parameters.length];
for(int i = 0; i < parameters.length; i++) {
if(Event.class.isAssignableFrom(parameters[i].getType()))
objects[i] = event;
}
simpleEvent.getMethod().invoke(simpleEvent.getObject(), objects);
}
// @Command(name = "helpEvent", group = "Help", grp = "hlp", description =
// "Affiche la liste des events existants", admin = true)
// public void helpEvent(Member member, Guild guild, MessageChannel channel)
// {
// try {
// EmbedBuilder eB = new EmbedBuilder();
// eB.setTitle("Liste des events: ");
// eB.setColor(DUtils.color);
//
// User user = member.getUser();
// if(!user.hasPrivateChannel())
// user.openPrivateChannel().complete();
//
// for(Entry entry : events.entrySet())
// eB.addField(entry.getKey().toString(),
// ((EventObject)entry.getValue()).getDescription(), false);
// ((UserImpl)user).getPrivateChannel().sendMessage(eB.build()).queue();
// } catch(Exception e) {
// e.printStackTrace();
// }
// }
}

View File

@ -1,35 +0,0 @@
package com.bernard.discord.struct;
import java.lang.reflect.Method;
public class EventObject {
private final Class<?> clazz;
private final Object object;
private final Method method;
private final String description;
public EventObject(Class<?> clazz, Object object, String description, Method method) {
this.clazz = clazz;
this.object = object;
this.description = description;
this.method = method;
}
public Class<?> getClazz() {
return clazz;
}
public Object getObject() {
return object;
}
public Method getMethod() {
return method;
}
public String getDescription() {
return description;
}
}

View File

@ -0,0 +1,128 @@
package com.bernard.juliabot;
import java.sql.*;
import net.dv8tion.jda.client.events.call.GenericCallEvent;
import net.dv8tion.jda.client.events.group.GenericGroupEvent;
import net.dv8tion.jda.client.events.message.group.GenericGroupMessageEvent;
import net.dv8tion.jda.client.events.relationship.GenericRelationshipEvent;
import net.dv8tion.jda.core.events.Event;
import net.dv8tion.jda.core.events.channel.category.GenericCategoryEvent;
import net.dv8tion.jda.core.events.channel.priv.PrivateChannelCreateEvent;
import net.dv8tion.jda.core.events.channel.priv.PrivateChannelDeleteEvent;
import net.dv8tion.jda.core.events.channel.text.GenericTextChannelEvent;
import net.dv8tion.jda.core.events.channel.voice.GenericVoiceChannelEvent;
import net.dv8tion.jda.core.events.emote.GenericEmoteEvent;
import net.dv8tion.jda.core.events.guild.GenericGuildEvent;
import net.dv8tion.jda.core.events.guild.voice.GenericGuildVoiceEvent;
import net.dv8tion.jda.core.events.message.GenericMessageEvent;
import net.dv8tion.jda.core.events.message.MessageBulkDeleteEvent;
import net.dv8tion.jda.core.events.message.guild.GenericGuildMessageEvent;
import net.dv8tion.jda.core.events.message.priv.GenericPrivateMessageEvent;
import net.dv8tion.jda.core.events.message.react.MessageReactionAddEvent;
import net.dv8tion.jda.core.events.role.GenericRoleEvent;
import net.dv8tion.jda.core.events.user.GenericUserEvent;
import net.dv8tion.jda.core.hooks.EventListener;
public class EcouteurDEvents implements EventListener{
public EcouteurDEvents() {
// TODO Auto-generated constructor stub
}
@Override
public void onEvent(Event event) {
Thread dbRunner = new Thread(new DbRunner(event),"dbRunner-"+System.nanoTime());
dbRunner.start();
Julia.theJulia.laboratoires.get(getLabo(event)).trigger(event);
}
public char getLabo(Event e) {
if(GenericMessageEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericMessageEvent)e).getChannel().getIdLong());
if(GenericGuildMessageEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericGuildMessageEvent)e).getChannel().getIdLong());
if(GenericUserEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericUserEvent)e).getUser().getIdLong());
if(GenericGuildVoiceEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericGuildVoiceEvent)e).getVoiceState().getChannel().getIdLong());
if(GenericGuildEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericGuildEvent)e).getGuild().getIdLong());
if(GenericPrivateMessageEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericPrivateMessageEvent)e).getChannel().getIdLong());
if(e.getClass() == MessageBulkDeleteEvent.class)
return g(((MessageBulkDeleteEvent)e).getChannel().getIdLong());
if(GenericTextChannelEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericTextChannelEvent)e).getGuild().getIdLong());
if(GenericVoiceChannelEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericVoiceChannelEvent)e).getGuild().getIdLong());
if(GenericCategoryEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericCategoryEvent)e).getGuild().getIdLong());
if(GenericRoleEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericRoleEvent)e).getGuild().getIdLong());
if(GenericEmoteEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericEmoteEvent)e).getGuild().getIdLong());
if(e.getClass() == PrivateChannelCreateEvent.class)
return g(((PrivateChannelCreateEvent)e).getUser().getIdLong());
if(e.getClass() == PrivateChannelDeleteEvent.class)
return g(((PrivateChannelDeleteEvent)e).getUser().getIdLong());
if(GenericRelationshipEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericRelationshipEvent)e).getUser().getIdLong());
if(GenericGroupEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericGroupEvent)e).getGroup().getIdLong());
if(GenericGroupMessageEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericEmoteEvent)e).getGuild().getIdLong());
if(GenericCallEvent.class.isAssignableFrom(e.getClass()))
return g(((GenericCallEvent)e).getCall().isGroupCall()?((GenericCallEvent)e).getCall().getGroup().getIdLong():((GenericCallEvent)e).getCall().getPrivateChannel().getUser().getIdLong());
return '#';
}
public Character g(Long id) {
return Julia.theJulia.laboratoriesIdentifieurs.getOrDefault(id, '#');
}
public class DbRunner implements Runnable{
Event event;
public DbRunner(Event event) {
this.event = event;
}
@Override
public void run() {
PreparedStatement s;
Connection db = Julia.theJulia.eventDatabase;
try {
switch(event.getClass().getName()) {
case "net.dv8tion.jda.core.events.message.react.MessageReactionAddEvent":
MessageReactionAddEvent e = (MessageReactionAddEvent) event;
s = db.prepareStatement("INSERT INTO messageReactionAdd VALUES (?,?,?,?,?,?,?,?,?,?)");
s.setLong(4, e.getMessageIdLong());
s.setLong(5, e.getChannel().getIdLong());
s.setLong(6, e.getGuild().getIdLong());
s.setLong(7, e.getUser().getIdLong());
s.setInt(8, e.getReaction().getCount());
s.setString(9, e.getReactionEmote().getName());
s.setLong(10, e.getReactionEmote().getIdLong());
break;
default: throw new IllegalStateException("Cette méthode n'est pas a jour avec le JDA ... je gère pas "+event.getClass().getName());
}
//(int ID,Datetime post-date,long responceNumber)
s.setNull(1, Types.INTEGER);
s.setDate(2, new Date(System.currentTimeMillis()));
s.setLong(3, event.getResponseNumber());
s.executeUpdate();
} catch (SQLException e1) {
System.err.println("Mysql pas content ......");
e1.printStackTrace();
}
}
}
}

View File

@ -0,0 +1,336 @@
package com.bernard.juliabot;
import java.io.File;
import java.io.IOException;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import com.bernard.juliabot.JuliaAddon.JarWithMultipleAddonsException;
import com.bernard.juliabot.JuliaAddon.JuliaClassLoader;
import com.bernard.juliabot.api.Command;
import com.bernard.juliabot.api.CommandCall;
import com.bernard.juliabot.api.Discord;
import net.dv8tion.jda.core.AccountType;
import net.dv8tion.jda.core.JDA;
import net.dv8tion.jda.core.JDABuilder;
import net.dv8tion.jda.core.events.Event;
public class Julia {
public static final String juliaddonsFolder = "/home/julia/juliaddons/";
private static final String token = "";
static Julia theJulia;
JDA jda;
Map<String,JuliaAddon> avalivableAddons;//pkg+version->addon
Map<Long,Character> laboratoriesIdentifieurs;//Store channels IDs ...
Map<Character,Laboratory> laboratoires;
Map<String,Long> fileTrack;//<File name in juliaddonFolder, lastModified>
Connection eventDatabase;
Connection juliaDatabase;
public Julia() {
avalivableAddons = new HashMap<>();
laboratoriesIdentifieurs = new HashMap<>();
laboratoires = new HashMap<>();
fileTrack = new HashMap<>();
//Set up mysql cnnections (events & data)
Properties connectionProps = new Properties();
connectionProps.put("user", "julia");
connectionProps.put("password", "juliabestbotever");
connectionProps.put("serverTimezone", "UTC");
connectionProps.put("verifyServerCertificate", "false");
connectionProps.put("useSSL", "true");
connectionProps.put("requireSSL", "true");
try {
eventDatabase = DriverManager.getConnection("jdbc:mysql://localhost:3306/juliaEvents", connectionProps);
juliaDatabase = DriverManager.getConnection("jdbc:mysql://localhost:3306/julia", connectionProps);
} catch (SQLException e) {
System.err.println("Impossible de se connecter a la BDD, ca ne sers a rien de lancer JuL'IA du coup ... Bonne nuit");
e.printStackTrace();
return;
}
//XXX sSet up JDA and Bot
try {
jda = new JDABuilder(AccountType.BOT).setToken(token).buildBlocking();
} catch(Exception e) {
System.err.println("Impossible de démarrer JuL'IA");
e.printStackTrace();
return;
}
//Launch update to see every addon in juliaddon/
update();//Va remplir la map avalivableAddons
//Load addons in # and in $ (récupere ce qu'il faut dans la BDD)
try {
Statement statement = juliaDatabase.createStatement();
ResultSet result = statement.executeQuery("SELECT * FROM loadedJuliaddons");
do {
char laboratory = result.getString("laboratory").charAt(0);
String pkg = result.getString("pkg");
String version = result.getString("version");
if(!laboratoires.containsKey(laboratory))
laboratoires.put(laboratory, new Laboratory(laboratory));
Laboratory labo = laboratoires.get(laboratory);
labo.loadAddon(pkg, version, false);//Pas besoin d'update, il viens d'etre fait
}while(result.next());
} catch (SQLException e) {
System.err.println("Impossible de charger les plugins, vous aurez tout a faire a la main !");
e.printStackTrace();
}
}
public synchronized void update() {
Map<String,JuliaAddon> avalivableAddons = new HashMap<>();
File juliaddonFolder = new File(juliaddonsFolder);
for(File f : juliaddonFolder.listFiles((parent,name)->name.toLowerCase().endsWith(".jar"))){
if(fileTrack.get(f.getName()) == f.lastModified())
continue;//Le fichier n'a pas bougé, pas besoin de le relire
fileTrack.put(f.getName(), f.lastModified());
try {
JarFile jar = new JarFile(f);
try {
JuliaAddon addon = new JuliaAddon(jar);
String id = addon.pkg+":"+addon.version;
if(avalivableAddons.containsKey(id))
System.err.println("L'addon "+id+" a déjà été chargé dans les fichiers "+avalivableAddons.get(id).jarFile.getName()+" et "+jar.getName()+", je garde que le deuxième !");
avalivableAddons.put(id, addon);
}catch(JarWithMultipleAddonsException e) {
Set<Set<JarEntry>> addonsEntries = e.getAddonsEntries();
for (Set<JarEntry> entry : addonsEntries) {
try {
JuliaAddon addon = new JuliaAddon(jar, entry);
String id = addon.pkg+":"+addon.version;
if(avalivableAddons.containsKey(id))
System.err.println("L'addon "+id+" a déjà été chargé dans les fichiers "+avalivableAddons.get(id).jarFile.getName()+" et "+jar.getName()+", je garde que le deuxième !");
avalivableAddons.put(id, addon);
} catch (JarWithMultipleAddonsException e1) {
System.err.println("THIS SHOULD NOT HAPPEN");
System.err.println("TOUT EST CASSÉ ALERTE ROUGE !");
System.err.println("C'est problematique, j'eteint tout, c'est mieux");
System.exit(31415926);
}
}
}
} catch (IOException e) {
System.err.println("Impossible de lire le fichier jar "+f.getName());
e.printStackTrace();
}
}
this.avalivableAddons = avalivableAddons;
}
public class Laboratory{
char laboratory;
Map<String,JuliaAddon> loadedAddons;//<pkg,JuliaAddon>
Map<String,Method> loadedCommands;
Map<Class<?>,Object> callerObjects;
Map<String,String> aliases;
Map<Class<? extends Event>,Set<Method>> loadedEvents;
Map<String,JuliaClassLoader> clazzTrack;//<className,JuliaClassLoader which loaded ths class in this laboratory>
public Laboratory(char laboratory) {
this.laboratory = laboratory;
loadedAddons = new HashMap<>();
loadedCommands = new HashMap<>();
aliases = new HashMap<>();
loadedEvents = new HashMap<>();
clazzTrack = new HashMap<>();
}
public JuliaClassLoader findClassLoader(String className) {
return clazzTrack.get(className);
}
public void reloadAddon(String pkg,String version) {
unloadAddon(pkg);
loadAddon(pkg, version);
}
public void loadAddon(String pkg,String version) {
this.loadAddon(pkg, version, true);
}
public synchronized void loadAddon(String pkg,String version,boolean update) {
if(update)Julia.this.update();
if(loadedAddons.containsKey(pkg))
throw new IllegalStateException("Impossible de charger le juliaddon "+pkg+" dans le laboratoire "+laboratory+", il est déjà chargé");
try {
PreparedStatement s = juliaDatabase.prepareStatement("INSERT INTO juliaddons (laboratory,pkg,version) VALUES (?,?,?)");
s.setString(1, Character.toString(laboratory));
s.setString(2, pkg);
s.setString(3, version);
s.executeUpdate();
} catch (SQLException e) {
System.err.println("Je ne peux pas notifier la BDD que je load le plugin, je le load pas du coup ...");
e.printStackTrace();
return;
}
JuliaAddon addon = Julia.this.avalivableAddons.get(pkg+":"+version);
if(addon == null)
throw new IllegalArgumentException("L'addon "+pkg+" n'est pas disponible dans sa version "+version);
JuliaClassLoader classLoader = addon.newClassLoader(this);
classLoader.registerCommandsAndEvents();
loadedAddons.put(pkg, addon);
}
public synchronized void unloadAddon(String pkg) {
if(!loadedAddons.containsKey(pkg))
return;//SI l'addon n'est pas chargé, on a rien besoin de faire
try {
PreparedStatement s = juliaDatabase.prepareStatement("DELETE FROM juliaddons WHERE laboratory=? AND pkg=?");
s.setString(1, Character.toString(laboratory));
s.setString(2, pkg);
if(s.executeUpdate() != 1) {
System.err.println("Ce juliaddon n'était pas chargé dans la BDD ... très bizzare");
}
} catch (SQLException e) {
System.err.println("Je ne peux pas notifier la BDD que je unload le plugin, je l'unload mais vous risquez d'avoir des problemes ...");
e.printStackTrace();
return;
}
JuliaAddon addon = loadedAddons.get(pkg);
addon.classLoaders.get(this.laboratory).unregisterCommandsAndEvents();
loadedAddons.remove(pkg);
}
public synchronized void registerCommand(Method m,Command c) {
if(loadedCommands.containsKey(c.name()))
throw new IllegalStateException("Une commade "+c.name()+" a déjà été enregistrée !");
//Verify that commands asks for good argument
Class<?>[] parameters = m.getParameterTypes();
if(parameters.length > 1)
throw new IllegalArgumentException("La méthode d'une commande ne peux prendre au maximum qu'un argument (de type CommandCall), la méthode fautive étant "+m.toGenericString());
if(parameters.length == 1 && parameters[0] == CommandCall.class)
throw new IllegalArgumentException("La méthode d'une commande, si elle possede un argument, ce dernier doit tre de type CommandCall, la méthode fautive étant "+m.toGenericString());
// Argument OK
//Register aliases
for(String alias:c.aliases()) {
if(aliases.containsKey(alias))
System.err.println("Faut remplacer l'alias "+alias+", plus de deux addons l'utilisent");
aliases.put(alias, c.name());
}
//Création de l'objet si ca n'a pas été fait
checkObject(m.getDeclaringClass());
loadedCommands.put(c.name(), m);
}
@SuppressWarnings("unchecked")//It is, in reallity checked
public synchronized void registerEvent(Method m, Discord d) {
Class<?>[] parameters = m.getParameterTypes();
if(parameters.length != 1)
throw new IllegalArgumentException("Les catcheurs d'events ne doivent avoir qu'un seul paramètre, extends Event, la méthde fautive étant "+m.toGenericString());
if(Event.class.isAssignableFrom(parameters[0]))
throw new IllegalArgumentException("Les catcheur d'events ne doivent avoir qu'un paramètre, qui doit extends Event, la méthode fautive étant "+m.toGenericString());
//La méthode est vérifiée
if(!loadedEvents.containsKey(parameters[0]))
loadedEvents.put((Class<? extends Event>) parameters[0], new HashSet<>());
checkObject(m.getDeclaringClass());
loadedEvents.get(parameters[0]).add(m);
}
public synchronized void unregisterCommand(Method m,Command c) {
if(loadedCommands.containsKey(c.name()))
throw new IllegalStateException("Une commade "+c.name()+" a déjà été enregistrée !");
//Unregister aliases
for(String alias:c.aliases())
aliases.remove(alias, c.name());//Evite de supprimer les alias d'autres commandes qui auraient overwrite
loadedCommands.remove(c.name());
}
@SuppressWarnings("unchecked")//Pour un truc qui n'ets pas censé arriver, donc bon ...
public synchronized void unregisterEvent(Method m, Discord d) {
Class<?>[] parameters = m.getParameterTypes();
if(!loadedEvents.containsKey(parameters[0]))//N'est pas censé arriver, si l'event a été load, cette HashSet devrai exister
loadedEvents.put((Class<? extends Event>) parameters[0], new HashSet<>());
loadedEvents.get(parameters[0]).remove(m);
}
public void checkObject(Class<?> clazz) {
if(!callerObjects.containsKey(clazz)) {
//Chercher un bon constructeur
Object o = null;
constLoop : for(Constructor<?> constructor : clazz.getConstructors()) {
try {
Class<?>[] paramsTypes = constructor.getParameterTypes();
Object[] params = new Object[paramsTypes.length];
for (int i = 0; i < params.length; i++) {
switch(paramsTypes[i].getName()) {
case "java.lang.Character":
params[i] = this.laboratory;
break;
default:
continue constLoop;
}
}
o = constructor.newInstance(params);
} catch (SecurityException | InstantiationException | IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
//Tant pis, constructeur suivant
continue constLoop;
}
if(o != null)break;//Sortir de la boucle, on a notre juli objet
}
if(o == null) {
System.err.println("Je ne peux pas créer l'objet, faudait mettre un costructeur valide (en mon sens :P)");
System.err.println("Je fais tout planter du coup, votrez addon sera pas chargé !");
throw new IllegalStateException("Pas de constructeur valable");
}
}
}
public void trigger(Event event) {
// TODO Auto-generated method stub
}
}
public static void main(String[] args) {
theJulia = new Julia();
}
public static Julia theJulia() {
return theJulia;
}
}

View File

@ -0,0 +1,274 @@
package com.bernard.juliabot;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Method;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import com.bernard.juliabot.api.Command;
import com.bernard.juliabot.api.Discord;
import com.bernard.juliabot.Julia.Laboratory;
import com.bernard.juliabot.api.JuLIAddon;
public class JuliaAddon {
private static final Pattern pkgFromClassName = Pattern.compile("^(\\w(\\.\\w){2,})\\.\\w(\\$\\w)*$");
private static final Pattern jarNameParser = Pattern.compile("^([^_])_([^_])(_(.*))?.jar$");
String pkg;
String version;
JarFile jarFile;
long lastModified;
Set<JarEntry> loaderEntries;
Map<Character,JuliaClassLoader> classLoaders;
JuliaClassLoader unassignedClassLoader = null;
JuLIAddon addon;
Class<?> addonClass;
public JuliaAddon(JarFile jar) throws JarWithMultipleAddonsException {
this(jar,jar.stream().collect(Collectors.toSet()));
}
public JuliaAddon(JarFile jar,Set<JarEntry> entriesToRead) throws JarWithMultipleAddonsException {
jarFile = jar;
loaderEntries = entriesToRead;
lastModified = new File(jar.getName()).lastModified();
classLoaders = new HashMap<>();
//Parsing du nom du fichier
Matcher jarMatcher = jarNameParser.matcher(jar.getName());
jarMatcher.matches();
//String jarAddonName = jarMatcher.group(1);
String jarVersion = jarMatcher.group(2);
//String jarExtra = jarMatcher.group(3);
version = jarVersion;
//Sets addon,pkg,version(si redefini) et addonClass
unassignedClassLoader = new JuliaClassLoader(jar, entriesToRead);
}
public synchronized JuliaClassLoader newClassLoader(Laboratory laboratory) {
if(unassignedClassLoader==null)
try {
JuliaClassLoader cl = new JuliaClassLoader(jarFile, loaderEntries);
cl.laboratory = laboratory;
classLoaders.put(laboratory.laboratory, cl);
return cl;
} catch (JarWithMultipleAddonsException e) {
System.err.println("Cette erreur n'est pas censée arriver, alerte rouge");
System.exit(685533990);
}
JuliaClassLoader cl = unassignedClassLoader;
unassignedClassLoader = null;
cl.laboratory = laboratory;
classLoaders.put(laboratory.laboratory, cl);
return cl;
}
public String getName() {
return addon.name();
}
public class JuliaClassLoader extends ClassLoader {
Map<String,Class<?>> loadedClasses;
Laboratory laboratory = null;
HashSet<Method> registeredCommands;
HashSet<Method> registeredEvents;
public JuliaClassLoader(JarFile jar,Set<JarEntry> entriesToRead) throws JarWithMultipleAddonsException {
super();
Set<Class<?>> readClasses = new HashSet<>();
Map<String,JarEntry> juliaddons = new HashMap<>();
for(JarEntry entry : entriesToRead) {
if(entry.isDirectory())
continue;
if(!entry.getName().endsWith(".class"))
continue;
//Le fichier est un .class
try {
String className = entry.getName().replaceAll("/", ".").substring(0, entry.getName().length()-".class".length());
byte[] classData = new byte[(int) entry.getSize()];
InputStream reader = jar.getInputStream(entry);
reader.read(classData);
reader.close();
Class<?> clazz = defineClass(className,classData,0,(int) entry.getSize());
readClasses.add(clazz);
//Instantiated class
if(clazz.isAnnotationPresent(JuLIAddon.class)) {
//Declare package and new addon
Matcher m = pkgFromClassName.matcher(clazz.getName());
if(!m.matches())
throw new IllegalArgumentException("Le nom de la classe est invalide pour un Juliaddon (il faut au moins trois de profondeur dans le package) : "+clazz.getName());
String pkg = m.group(1);
if(juliaddons.containsKey(pkg))
throw new IllegalArgumentException("Il existe deja un juliaddon dans le package "+pkg+" , déplacez "+clazz.getName()+" ou "+juliaddons.get(pkg).getName());
juliaddons.put(pkg, entry);
//If overwritten, will JarWithMultipleAddonsException
JuliaAddon.this.addon = clazz.getAnnotation(JuLIAddon.class);
JuliaAddon.this.pkg = pkg;
JuliaAddon.this.version = addon.version().isEmpty()?version:addon.version();
JuliaAddon.this.addonClass = clazz;
}
}catch (ClassFormatError e) {
System.err.println("Impossible de lire cette classe, son format est incorrect ... veuillez recompiler le jar");
e.printStackTrace();
continue;
}catch(SecurityException e) {
System.err.println("Vous essayez de mettre cette classe dans un package interdit ! Honte a vous");
e.printStackTrace();
continue;
} catch (IOException e) {
System.err.println("Impossible de lire les données du fichier "+entry.getName()+" dans le jar "+jar.getName());
e.printStackTrace();
continue;
} catch (IllegalArgumentException e) {
System.err.println("Le fichier "+entry.getName()+" ne décris pas un Juliaddon valide, il n'a donc pas été chargé, mais faites attention !");
e.printStackTrace();
continue;
}
}
//Toutes les classes du Jar ont été lues : Si plusieurs addons, on rentre
//dans le if pour lever l'exception, sinon, on initialise le JuliaClassLoader
if(juliaddons.size() > 1) {
Set<Set<JarEntry>> addonsEntries = new HashSet<>();//<pkg,Enum of classes associated with this plugin>
Map<String,Set<JarEntry>> addonsEntriesVector = new HashMap<>();
for (String pkg : juliaddons.keySet())
addonsEntriesVector.put(pkg, new HashSet<>());
eLoop : for(JarEntry entry : entriesToRead) {
if(entry.isDirectory())
continue;
if(!entry.getName().endsWith(".class"))
continue;
//Le fichier est un .class, a placer dans le bon addon
String pkg = entry.getName().replaceAll("/", ".").substring(0, entry.getName().length()-".class".length());
int lastPoint;
while((lastPoint = pkg.lastIndexOf(".")) != -1) {//Il y a encore des dossier a monter
pkg = pkg.substring(0, lastPoint+1);//Recule de un dossier
if(addonsEntriesVector.containsKey(pkg)) {
//Pas besoin de tester la validite du pkg car si invalide il ne serai pas rentré dans le Set juliaddons
addonsEntriesVector.get(pkg).add(entry);
continue eLoop;
}
}
//Si le code atteint ici, le JarEntry n'appartient a aucun pkg valide
System.err.println("Ce jar contiens plusieurs juliaddons. Nichtsdestotroz le fichier "+entry.getName()+" n'a pas de Juliaddon dans son package ou au dessus ... je ne charge donc pas la classe (attention, ca peux ammener a des ClassNotFoundException !!!)");
continue;
}
addonsEntries = new HashSet<>(addonsEntriesVector.values());
throw new JarWithMultipleAddonsException(addonsEntries);
}
//Initialisation du JuliaClassloader
//Les parametres addon, pkg,version et addonCLass ont déjà été initialisés lors de l'itération des fichiers du jar
loadedClasses = new HashMap<>();
for(Class<?> clazz : readClasses)
loadedClasses.put(clazz.getName(), clazz);
}
@Override
public Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException {
if(loadedClasses.containsKey(name))
return loadedClasses.get(name);
JuliaClassLoader cl = laboratory.findClassLoader(name);
if(cl != null)
try {
return cl.loadClass(name, resolve);
}catch(ClassNotFoundException e) {
throw new ClassNotFoundException("J'ai délégué le chargement de la classe mais j'aurais pas du ... cette classe ne doit pas exister dans l'addon "+cl.getAddon().getName(),e);
}
else
try {
return ClassLoader.getSystemClassLoader().loadClass(name);
}catch(ClassNotFoundException e) {
throw new ClassNotFoundException("Cette classe n'est nul part ... elle ne doit pas exister ou alors elle est dans un mauvais packet !",e);
}
}
public void registerCommandsAndEvents() {
registeredCommands = new HashSet<>();
registeredEvents = new HashSet<>();
Set<Method> toWatch = new HashSet<>();
Collections.addAll(toWatch, JuliaAddon.this.addonClass.getMethods());
for (Class<?> clazz : JuliaAddon.this.addon.searchPath())
try {
Collections.addAll(toWatch, loadClass(clazz.getName()).getMethods());//loadClass(clazz.getName()) poir eviter les references cassees par les classloaders
} catch (SecurityException | ClassNotFoundException e) {
e.printStackTrace();
System.err.println("L'addon "+JuliaAddon.this.addonClass.getName()+" spécifie la classe "+clazz.getName());
}
for(Method m : toWatch) {
Command c = m.getAnnotation(Command.class);
Discord d = m.getAnnotation(Discord.class);
if(c != null) {
registeredCommands.add(m);
laboratory.registerCommand(m, c);
}else if(d != null) {
registeredEvents.add(m);
laboratory.registerEvent(m, d);
}
}
}
public void unregisterCommandsAndEvents() {
for(Method m : registeredCommands) {
Command c = m.getAnnotation(Command.class);
registeredCommands.add(m);
laboratory.unregisterCommand(m, c);
}
for(Method m : registeredEvents) {
Discord d = m.getAnnotation(Discord.class);
registeredEvents.add(m);
laboratory.unregisterEvent(m, d);
}
registeredCommands.clear();
registeredEvents.clear();
}
public JuliaAddon getAddon() {
return JuliaAddon.this;
}
}
public static final class JarWithMultipleAddonsException extends Exception{
private static final long serialVersionUID = -7557959851687207287L;
Set<Set<JarEntry>> addonsEntries;
public JarWithMultipleAddonsException(Set<Set<JarEntry>> addonsEntries) {
this.addonsEntries = addonsEntries;
}
public Set<Set<JarEntry>> getAddonsEntries() {
return addonsEntries;
}
}
}

View File

@ -1,4 +1,4 @@
package com.bernard.discord.api;
package com.bernard.juliabot.api;
import java.lang.annotation.*;
@ -9,8 +9,6 @@ public @interface Command {
public String name();
public String[] aliases() default {};
public String description();
public String grp();
public String group();
public boolean admin();//TODO a remplacer par les permissions
}

View File

@ -1,4 +1,4 @@
package com.bernard.discord.api;
package com.bernard.juliabot.api;
import java.lang.annotation.*;

View File

@ -0,0 +1,19 @@
package com.bernard.juliabot.api;
import static java.lang.annotation.ElementType.TYPE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;
@Documented
@Retention(RUNTIME)
@Target(TYPE)
public @interface JuLIAddon {
String name();
String version() default "";
Class<?>[] searchPath() default {};
public String[] devs();
public boolean important() default false;
}