Added removing cmds from chat and perform method

The perform method handles safe mode and ratelimiting.
This commit is contained in:
Norbi Peti 2017-01-15 21:19:44 +01:00
parent 2b9164ebc6
commit dfeae5de9e
6 changed files with 101 additions and 90 deletions

View file

@ -1,7 +1,6 @@
package buttondevteam.discordplugin; package buttondevteam.discordplugin;
import java.awt.Color; import java.awt.Color;
import java.io.BufferedReader;
import java.io.File; import java.io.File;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.ArrayList; import java.util.ArrayList;
@ -24,7 +23,9 @@ import sx.blah.discord.api.events.IListener;
import sx.blah.discord.api.internal.json.objects.EmbedObject; import sx.blah.discord.api.internal.json.objects.EmbedObject;
import sx.blah.discord.handle.impl.events.ReadyEvent; import sx.blah.discord.handle.impl.events.ReadyEvent;
import sx.blah.discord.handle.obj.*; import sx.blah.discord.handle.obj.*;
import sx.blah.discord.util.DiscordException;
import sx.blah.discord.util.EmbedBuilder; import sx.blah.discord.util.EmbedBuilder;
import sx.blah.discord.util.MissingPermissionsException;
import sx.blah.discord.util.RateLimitException; import sx.blah.discord.util.RateLimitException;
public class DiscordPlugin extends JavaPlugin implements IListener<ReadyEvent> { public class DiscordPlugin extends JavaPlugin implements IListener<ReadyEvent> {
@ -230,37 +231,19 @@ public class DiscordPlugin extends JavaPlugin implements IListener<ReadyEvent> {
Bukkit.getLogger() Bukkit.getLogger()
.warning("Message was too long to send to discord and got truncated. In " + channel.getName()); .warning("Message was too long to send to discord and got truncated. In " + channel.getName());
} }
for (int i = 0; i < 10; i++) {
try { try {
Thread.sleep(i * 100);
} catch (InterruptedException e2) {
e2.printStackTrace();
}
try {
if (SafeMode)
return null;
if (channel == chatchannel) if (channel == chatchannel)
MCChatListener.resetLastMessage(); // If this is a chat message, it'll be set again MCChatListener.resetLastMessage(); // If this is a chat message, it'll be set again
final String content = TBMCCoreAPI.IsTestServer() && channel != chatchannel final String content = TBMCCoreAPI.IsTestServer() && channel != chatchannel
? "*The following message is from a test server*\n" + message : message; ? "*The following message is from a test server*\n" + message : message;
return embed == null ? channel.sendMessage(content) : channel.sendMessage(content, embed, false); return perform(
} catch (RateLimitException e) { () -> embed == null ? channel.sendMessage(content) : channel.sendMessage(content, embed, false));
try {
Thread.sleep(e.getRetryDelay());
} catch (InterruptedException e1) {
e1.printStackTrace();
}
} catch (Exception e) { } catch (Exception e) {
if (i == 9) { Bukkit.getLogger().warning(
Bukkit.getLogger().warning("Failed to deliver message to Discord! Channel: " + channel.getName() "Failed to deliver message to Discord! Channel: " + channel.getName() + " Message: " + message);
+ " Message: " + message);
throw new RuntimeException(e); throw new RuntimeException(e);
} else
continue;
} }
} }
return null;
}
public static Permission perms; public static Permission perms;
@ -296,4 +279,43 @@ public class DiscordPlugin extends JavaPlugin implements IListener<ReadyEvent> {
} }
return sanitizedString; return sanitizedString;
} }
/**
* Performs Discord actions, retrying when ratelimited. May return null if action fails too many times or in safe mode.
*/
public static <T extends IDiscordObject<T>> T perform(DiscordSupplier<T> action)
throws DiscordException, MissingPermissionsException {
for (int i = 0; i < 20; i++)
try {
if (SafeMode)
return null;
return action.get();
} catch (RateLimitException e) {
try {
Thread.sleep(e.getRetryDelay() > 0 ? e.getRetryDelay() : 10);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
}
return null;
}
/**
* Performs Discord actions, retrying when ratelimited.
*/
public static void perform(DiscordRunnable action) throws DiscordException, MissingPermissionsException {
for (int i = 0; i < 20; i++)
try {
if (SafeMode)
return;
action.run();
return; // Gotta escape that loop
} catch (RateLimitException e) {
try {
Thread.sleep(e.getRetryDelay() > 0 ? e.getRetryDelay() : 10);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
}
}
} }

View file

@ -0,0 +1,10 @@
package buttondevteam.discordplugin;
import sx.blah.discord.util.DiscordException;
import sx.blah.discord.util.MissingPermissionsException;
import sx.blah.discord.util.RateLimitException;
@FunctionalInterface
public interface DiscordRunnable {
public abstract void run() throws DiscordException, RateLimitException, MissingPermissionsException;
}

View file

@ -0,0 +1,11 @@
package buttondevteam.discordplugin;
import sx.blah.discord.handle.obj.IDiscordObject;
import sx.blah.discord.util.DiscordException;
import sx.blah.discord.util.MissingPermissionsException;
import sx.blah.discord.util.RateLimitException;
@FunctionalInterface
public interface DiscordSupplier<T extends IDiscordObject<T>> {
public abstract T get() throws DiscordException, RateLimitException, MissingPermissionsException;
}

View file

@ -7,7 +7,6 @@ import buttondevteam.discordplugin.DiscordPlugin;
import buttondevteam.lib.TBMCCoreAPI; import buttondevteam.lib.TBMCCoreAPI;
import sx.blah.discord.handle.obj.IMessage; import sx.blah.discord.handle.obj.IMessage;
import sx.blah.discord.handle.obj.IRole; import sx.blah.discord.handle.obj.IRole;
import sx.blah.discord.util.RateLimitException;
public class RoleCommand extends DiscordCommandBase { public class RoleCommand extends DiscordCommandBase {
@ -49,22 +48,15 @@ public class RoleCommand extends DiscordCommandBase {
"There are more roles with this name. Why are there more roles with this name?"); "There are more roles with this name. Why are there more roles with this name?");
return; return;
} }
while (true) {
try { try {
message.getAuthor().addRole(roles.get(0)); DiscordPlugin.perform(() -> message.getAuthor().addRole(roles.get(0)));
break;
} catch (RateLimitException e) {
try {
Thread.sleep(e.getRetryDelay() > 0 ? e.getRetryDelay() : 10);
} catch (InterruptedException e1) {
}
} catch (Exception e) { } catch (Exception e) {
TBMCCoreAPI.SendException("Error while adding role!", e); TBMCCoreAPI.SendException("Error while adding role!", e);
DiscordPlugin.sendMessageToChannel(message.getChannel(), "An error occured while adding the role."); DiscordPlugin.sendMessageToChannel(message.getChannel(), "An error occured while adding the role.");
break;
} }
} } else if (argsa[0].equalsIgnoreCase("remove"))
} else if (argsa[0].equalsIgnoreCase("remove")) {
{
if (argsa.length < 2) { if (argsa.length < 2) {
DiscordPlugin.sendMessageToChannel(message.getChannel(), DiscordPlugin.sendMessageToChannel(message.getChannel(),
"This command removes a game role from your account.\nUsage: remove <rolename>"); "This command removes a game role from your account.\nUsage: remove <rolename>");

View file

@ -10,7 +10,6 @@ import sx.blah.discord.api.events.IListener;
import sx.blah.discord.handle.impl.events.MessageReceivedEvent; import sx.blah.discord.handle.impl.events.MessageReceivedEvent;
import sx.blah.discord.handle.obj.IEmbed; import sx.blah.discord.handle.obj.IEmbed;
import sx.blah.discord.util.EmbedBuilder; import sx.blah.discord.util.EmbedBuilder;
import sx.blah.discord.util.RateLimitException;
public class AutoUpdaterListener implements IListener<MessageReceivedEvent> { public class AutoUpdaterListener implements IListener<MessageReceivedEvent> {
@Override @Override
@ -57,16 +56,8 @@ public class AutoUpdaterListener implements IListener<MessageReceivedEvent> {
} }
return true; return true;
}).get() && (!TBMCCoreAPI.IsTestServer() || !branch.equals("master"))) }).get() && (!TBMCCoreAPI.IsTestServer() || !branch.equals("master")))
while (true)
try { try {
event.getMessage().addReaction(DiscordPlugin.DELIVERED_REACTION); DiscordPlugin.perform(() -> event.getMessage().addReaction(DiscordPlugin.DELIVERED_REACTION));
break;
} catch (RateLimitException e) {
try {
if (e.getRetryDelay() > 0)
Thread.sleep(e.getRetryDelay());
} catch (InterruptedException ie) {
}
} catch (Exception e) { } catch (Exception e) {
TBMCCoreAPI.SendException("An error occured while reacting to plugin update!", e); TBMCCoreAPI.SendException("An error occured while reacting to plugin update!", e);
} }

View file

@ -46,8 +46,8 @@ public class MCChatListener implements Listener, IListener<MessageReceivedEvent>
try { try {
embedObject.description = lastmessage.getEmbedded().get(0).getDescription() + "\n" embedObject.description = lastmessage.getEmbedded().get(0).getDescription() + "\n"
+ embedObject.description; + embedObject.description;
lastmessage.edit("", embedObject); DiscordPlugin.perform(() -> lastmessage.edit("", embedObject));
} catch (MissingPermissionsException | RateLimitException | DiscordException e1) { } catch (MissingPermissionsException | DiscordException e1) {
TBMCCoreAPI.SendException("An error occured while editing chat message!", e1); TBMCCoreAPI.SendException("An error occured while editing chat message!", e1);
} }
} // TODO: Author URL } // TODO: Author URL
@ -130,7 +130,9 @@ public class MCChatListener implements Listener, IListener<MessageReceivedEvent>
} else } else
Bukkit.dispatchCommand(dsender, cmd); Bukkit.dispatchCommand(dsender, cmd);
lastlistp = (short) Bukkit.getOnlinePlayers().size(); lastlistp = (short) Bukkit.getOnlinePlayers().size();
} else if (!event.getMessage().isDeleted())
event.getMessage().delete();
} else {
TBMCChatAPI.SendChatMessage(Channel.GlobalChat, dsender, TBMCChatAPI.SendChatMessage(Channel.GlobalChat, dsender,
dmessage + (event.getMessage().getAttachments().size() > 0 ? "\n" + event.getMessage() dmessage + (event.getMessage().getAttachments().size() > 0 ? "\n" + event.getMessage()
.getAttachments().stream().map(a -> a.getUrl()).collect(Collectors.joining("\n")) .getAttachments().stream().map(a -> a.getUrl()).collect(Collectors.joining("\n"))
@ -138,30 +140,13 @@ public class MCChatListener implements Listener, IListener<MessageReceivedEvent>
event.getMessage().getChannel().getMessages().stream().forEach(m -> { event.getMessage().getChannel().getMessages().stream().forEach(m -> {
try { try {
final IReaction reaction = m.getReactionByName(DiscordPlugin.DELIVERED_REACTION); final IReaction reaction = m.getReactionByName(DiscordPlugin.DELIVERED_REACTION);
if (reaction != null) { if (reaction != null)
while (true) DiscordPlugin.perform(() -> m.removeReaction(reaction));
try {
m.removeReaction(reaction);
Thread.sleep(100);
break;
} catch (RateLimitException e) {
if (e.getRetryDelay() > 0)
Thread.sleep(e.getRetryDelay());
}
}
} catch (Exception e) { } catch (Exception e) {
TBMCCoreAPI.SendException("An error occured while removing reactions from chat!", e); TBMCCoreAPI.SendException("An error occured while removing reactions from chat!", e);
} }
}); });
while (true) DiscordPlugin.perform(() -> event.getMessage().addReaction(DiscordPlugin.DELIVERED_REACTION));
try {
event.getMessage().addReaction(DiscordPlugin.DELIVERED_REACTION);
break;
} catch (RateLimitException e) {
if (e.getRetryDelay() > 0)
Thread.sleep(e.getRetryDelay());
else
Thread.sleep(100);
} }
} catch (Exception e) { } catch (Exception e) {
TBMCCoreAPI.SendException("An error occured while handling message \"" + dmessage + "\"!", e); TBMCCoreAPI.SendException("An error occured while handling message \"" + dmessage + "\"!", e);