diff --git a/src/main/java/uk/co/angrybee/joe/DiscordClient.java b/src/main/java/uk/co/angrybee/joe/DiscordClient.java index 48d87fb..e4379a2 100644 --- a/src/main/java/uk/co/angrybee/joe/DiscordClient.java +++ b/src/main/java/uk/co/angrybee/joe/DiscordClient.java @@ -43,6 +43,8 @@ public class DiscordClient extends ListenerAdapter public static String[] allowedToAddLimitedRoles; public static String[] allowedToClearNamesRoles; + public static String[] combinedRoles; + private static String[] targetTextChannels; // TODO: remove in favour of split versions @@ -83,6 +85,7 @@ public class DiscordClient extends ListenerAdapter public static String[] whitelistedRoleNames; private static boolean checkForMissingRole = false; + private static boolean checkAllRoles = false; private static String roleToCheck; public static final char[] validCharacters = {'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', 'a', 's', 'd', 'f', 'g', 'h', @@ -161,6 +164,7 @@ public class DiscordClient extends ListenerAdapter } checkForMissingRole = mainConfig.getBoolean("un-whitelist-if-missing-role"); + checkAllRoles = mainConfig.getBoolean("check-all-roles"); roleToCheck = mainConfig.getString("role-to-check-for"); } @@ -1108,123 +1112,293 @@ public class DiscordClient extends ListenerAdapter CheckForRequiredRole(e); } - // TODO check users at startup for required role, in case it was removed while the bot was offline private static void CheckForRequiredRole(GuildMemberRoleRemoveEvent e) { if(!checkForMissingRole) return; - if(roleToCheck == null || roleToCheck.equals("")) - { - DiscordWhitelister.getPluginLogger().warning("'un-whitelist-if-missing-role' is enabled but " + - "'role-to-check-for' is null or empty, please double check the config"); - return; - } - - for(Role r : e.getMember().getRoles()) - { - // required role found, no need to proceed - if(r.getName().equals(roleToCheck)) - return; - } - String disName = e.getMember().getEffectiveName(); String disId = e.getMember().getId(); String nameForLogger = disName + "(" + disId + ")"; - DiscordWhitelister.getPluginLogger().info(nameForLogger + " does not have the required " + - "role (" + roleToCheck + "). Attempting to remove their whitelisted entries..."); - - List regUsers = UserList.getRegisteredUsers(disId); - if(regUsers != null) + if(checkAllRoles) { - if(regUsers.size() <= 0) + List removedRoles = e.getRoles(); + boolean limitedRoleRemoved = false; + + // Check if removed roles contain a limited-add role + for(Role role:removedRoles) { - DiscordWhitelister.getPluginLogger().info(nameForLogger + "'s entries are empty, doing nothing"); + if(Arrays.asList(allowedToAddLimitedRoles).contains(role.getName())) + { + limitedRoleRemoved = true; + break; + } + } + + if(!limitedRoleRemoved) return; + + DiscordWhitelister.getPlugin().getLogger().info(nameForLogger + "'s limited role(s) has been removed. Checking for remaining roles..."); + boolean rolesRemaining= false; + for(int i = 0; i < javaDiscordAPI.getGuilds().size(); i++) + { + Member member = javaDiscordAPI.getGuilds().get(i).getMemberById(disId); + if(member != null) + { + List roles = member.getRoles(); + for(Role role:roles) + { + if(Arrays.asList(combinedRoles).contains(role.getName())) + { + rolesRemaining = true; + break; + } + } + } } - for(Object mcName : regUsers) + if(!rolesRemaining) { - UnWhitelist(mcName.toString()); - } + DiscordWhitelister.getPlugin().getLogger().info(nameForLogger + " has no roles remaining. Removing their whitelisted entries..."); - try - { - UserList.resetRegisteredUsers(disId); - } - catch (IOException ex) - { - DiscordWhitelister.getPluginLogger().severe("Failed to remove whitelisted users from " + - nameForLogger); - ex.printStackTrace(); - return; - } + List ls = UserList.getRegisteredUsers(disId); + if(ls != null) + { + for (Object minecraftNameToRemove : ls) + { + UnWhitelist(minecraftNameToRemove.toString()); + } - DiscordWhitelister.getPluginLogger().info("Successfully removed " + nameForLogger + - "'s whitelisted entries due to missing required role (" + roleToCheck + ")"); + try + { + UserList.resetRegisteredUsers(disId); + } + catch (IOException ex) + { + ex.printStackTrace(); + } + } + else + { + DiscordWhitelister.getPlugin().getLogger().warning(nameForLogger + " does not have any whitelisted entries doing nothing..."); + } + } + else + { + DiscordWhitelister.getPlugin().getLogger().info(nameForLogger + " has role(s) remaining. Doing nothing..."); + } } else { - DiscordWhitelister.getPluginLogger().warning("Failed to remove whitelisted entries from " + - nameForLogger + " as they did not whitelist through this plugin"); - } - } - - public static void RequiredRoleStartupCheck() { - try { - if (!checkForMissingRole) - return; - - if (roleToCheck == null || roleToCheck.equals("")) { + if(roleToCheck == null || roleToCheck.equals("")) + { DiscordWhitelister.getPluginLogger().warning("'un-whitelist-if-missing-role' is enabled but " + "'role-to-check-for' is null or empty, please double check the config"); return; } - DiscordWhitelister.getPluginLogger().info("Checking Discord IDs for required roles..."); + for(Role r : e.getMember().getRoles()) + { + // required role found, no need to proceed + if(r.getName().equals(roleToCheck)) + return; + } - Yaml idYaml = new Yaml(); - UserList.SaveStore(); - InputStream inputStream = new FileInputStream(UserList.getUserListFile()); + DiscordWhitelister.getPluginLogger().info(nameForLogger + " does not have the required " + + "role (" + roleToCheck + "). Attempting to remove their whitelisted entries..."); - PushbackInputStream pushbackInputStream = new PushbackInputStream(inputStream); - int b = pushbackInputStream.read(); + List regUsers = UserList.getRegisteredUsers(disId); + if(regUsers != null) + { + if(regUsers.size() <= 0) + { + DiscordWhitelister.getPluginLogger().info(nameForLogger + "'s entries are empty, doing nothing"); + return; + } - if (b == -1) - return; + for(Object mcName : regUsers) + { + UnWhitelist(mcName.toString()); + } + + try + { + UserList.resetRegisteredUsers(disId); + } + catch (IOException ex) + { + DiscordWhitelister.getPluginLogger().severe("Failed to remove whitelisted users from " + + nameForLogger); + ex.printStackTrace(); + return; + } + + DiscordWhitelister.getPluginLogger().info("Successfully removed " + nameForLogger + + "'s whitelisted entries due to missing required role (" + roleToCheck + ")"); + } else - pushbackInputStream.unread(b); + { + DiscordWhitelister.getPluginLogger().warning("Failed to remove whitelisted entries from " + + nameForLogger + " as they did not whitelist through this plugin"); + } + } + } - Map> userObject = idYaml.load(pushbackInputStream); + public static void RequiredRoleStartupCheck() + { + try + { + if (!checkForMissingRole) + return; - for (Map.Entry> entry : userObject.entrySet()) { - // Check if the ID is in any guilds - boolean hasRole = false; + // Don't attempt to remove roles if not connected + if (javaDiscordAPI.getStatus() != JDA.Status.CONNECTED) + return; - // Check all guilds - boolean requiredRole = false; - for (int i = 0; i < javaDiscordAPI.getGuilds().size(); i++) { - Member member = javaDiscordAPI.getGuilds().get(i).getMemberById(entry.getKey()); - if (member != null) { - for (Role role : member.getRoles()) { - if (role.getId().equals(roleToCheck)) { - requiredRole = true; - break; + if (checkAllRoles) + { + DiscordWhitelister.getPluginLogger().info("Checking Discord IDs for required roles..."); + + Yaml idYaml = new Yaml(); + UserList.SaveStore(); + InputStream inputStream = new FileInputStream(UserList.getUserListFile()); + + PushbackInputStream pushbackInputStream = new PushbackInputStream(inputStream); + int b = pushbackInputStream.read(); + + if (b == -1) + return; + else + pushbackInputStream.unread(b); + + Map> userObject = idYaml.load(pushbackInputStream); + + for (Map.Entry> entry : userObject.entrySet()) + { + // Check all guilds + boolean rolesRemaining = false; + for (int i = 0; i < javaDiscordAPI.getGuilds().size(); i++) + { + Member member = javaDiscordAPI.getGuilds().get(i).getMemberById(entry.getKey()); + + if (member != null) + { + List roles = member.getRoles(); + for (Role role : roles) + { + if (Arrays.asList(combinedRoles).contains(role.getName())) + { + rolesRemaining = true; + break; + } + } + } + } + + if (!rolesRemaining) + { + DiscordWhitelister.getPlugin().getLogger().info(entry.getKey() + " has no roles remaining. Removing their whitelisted entries..."); + + if(entry.getValue() == null || entry.getValue().size() <= 0) + { + DiscordWhitelister.getPluginLogger().info("User ID: " + entry.getKey() + "has no whitelisted users, doing nothing..."); + } + else + { + for(String wUser : entry.getValue()) + { + UnWhitelist(wUser); + } + + // Clear entries in user-list + if (userObject.get(entry.getKey()) != null) + { + UserList.getUserList().set(entry.getKey(), null); + UserList.SaveStore(); + + DiscordWhitelister.getPlugin().getLogger().info("Successfully removed " + entry.getKey() + " whitelisted entries from the user list."); } } } } - if (!requiredRole) { - for (int i = 0; i < entry.getValue().size(); i++) { - // un-whitelist - UnWhitelist(entry.getValue().get(i)); - DiscordWhitelister.getPluginLogger().info("Removed " + entry.getValue().get(i) - + " from the whitelist as Discord ID: " + entry.getKey() + " due to missing required role (" + roleToCheck + ")."); + } + else + { + if (roleToCheck == null || roleToCheck.equals("")) + { + DiscordWhitelister.getPluginLogger().warning("'un-whitelist-if-missing-role' is enabled but " + + "'role-to-check-for' is null or empty, please double check the config"); + return; + } + + DiscordWhitelister.getPluginLogger().info("Checking Discord IDs for required role " + roleToCheck); + + Yaml idYaml = new Yaml(); + UserList.SaveStore(); + InputStream inputStream = new FileInputStream(UserList.getUserListFile()); + + PushbackInputStream pushbackInputStream = new PushbackInputStream(inputStream); + int b = pushbackInputStream.read(); + + if (b == -1) + return; + else + pushbackInputStream.unread(b); + + Map> userObject = idYaml.load(pushbackInputStream); + + for (Map.Entry> entry : userObject.entrySet()) + { + // Check all guilds + boolean requiredRole = false; + for (int i = 0; i < javaDiscordAPI.getGuilds().size(); i++) + { + Member member = javaDiscordAPI.getGuilds().get(i).getMemberById(entry.getKey()); + if (member != null) + { + for (Role role : member.getRoles()) + { + if (role.getId().equals(roleToCheck)) + { + requiredRole = true; + break; + } + } + } + } + + if (!requiredRole) + { + if(entry.getValue() != null && entry.getValue().size() <= 0) + { + DiscordWhitelister.getPluginLogger().info("User ID: " + entry.getKey() + "has no whitelisted users, doing nothing..."); + } + else + { + for (int i = 0; i < entry.getValue().size(); i++) + { + // un-whitelist + UnWhitelist(entry.getValue().get(i)); + DiscordWhitelister.getPluginLogger().info("Removed " + entry.getValue().get(i) + + " from the whitelist as Discord ID: " + entry.getKey() + " due to missing required role (" + roleToCheck + ")."); + } + } + + // Clear entries in user-list + if (userObject.get(entry.getKey()) != null) + { + UserList.getUserList().set(entry.getKey(), null); + UserList.SaveStore(); + + DiscordWhitelister.getPlugin().getLogger().info("Successfully removed " + entry.getKey() + " whitelisted entries from the user list."); + } } } } - } catch (IOException e) { + } + catch (IOException e) + { e.printStackTrace(); } } diff --git a/src/main/java/uk/co/angrybee/joe/DiscordWhitelister.java b/src/main/java/uk/co/angrybee/joe/DiscordWhitelister.java index f937a9a..6ca13d5 100755 --- a/src/main/java/uk/co/angrybee/joe/DiscordWhitelister.java +++ b/src/main/java/uk/co/angrybee/joe/DiscordWhitelister.java @@ -17,6 +17,7 @@ import uk.co.angrybee.joe.stores.WhitelistedPlayers; import java.util.List; import java.util.logging.Logger; +import java.util.stream.Stream; public class DiscordWhitelister extends JavaPlugin { @@ -219,6 +220,11 @@ public class DiscordWhitelister extends JavaPlugin DiscordClient.allowedToClearNamesRoles[roles] = MainConfig.getMainConfig().getStringList("clear-command-roles").get(roles); } + // All roles combined for role check + DiscordClient.combinedRoles = Stream.of(DiscordClient.allowedToAddRemoveRoles, DiscordClient.allowedToAddRoles, + DiscordClient.allowedToAddLimitedRoles, DiscordClient.allowedToClearNamesRoles) + .flatMap(Stream::of).toArray(String[]::new); + // Custom messages check useCustomMessages = MainConfig.getMainConfig().getBoolean("use-custom-messages"); useCustomPrefixes = MainConfig.getMainConfig().getBoolean("use-custom-prefixes"); diff --git a/src/main/java/uk/co/angrybee/joe/configs/MainConfig.java b/src/main/java/uk/co/angrybee/joe/configs/MainConfig.java index e52447b..e9b7afc 100644 --- a/src/main/java/uk/co/angrybee/joe/configs/MainConfig.java +++ b/src/main/java/uk/co/angrybee/joe/configs/MainConfig.java @@ -163,6 +163,8 @@ public class MainConfig CheckEntry("un-whitelist-if-missing-role", false); + CheckEntry("check-all-roles", false); + CheckEntry("role-to-check-for", "Twitch Subscriber"); // Remove old role entry if found, move role to new array (for people with v1.3.6 or below)