diff --git a/Figures for documentation/Resolution of permission tree New.pptx b/Figures for documentation/Resolution of permission tree New.pptx new file mode 100644 index 0000000..9eb47d0 Binary files /dev/null and b/Figures for documentation/Resolution of permission tree New.pptx differ diff --git a/src/main/java/ru/simsonic/rscPermissions/API/BridgeForBukkitAPI.java b/src/main/java/ru/simsonic/rscPermissions/API/BridgeForBukkitAPI.java index 9a0e7a2..2f85f60 100644 --- a/src/main/java/ru/simsonic/rscPermissions/API/BridgeForBukkitAPI.java +++ b/src/main/java/ru/simsonic/rscPermissions/API/BridgeForBukkitAPI.java @@ -32,4 +32,12 @@ public class BridgeForBukkitAPI { return this.vaultChat; } + public String getName() + { + return rscp.getDescription().getName(); + } + public boolean isEnabled() + { + return rscp.isEnabled(); + } } diff --git a/src/main/java/ru/simsonic/rscPermissions/API/PlayerType.java b/src/main/java/ru/simsonic/rscPermissions/API/PlayerType.java new file mode 100644 index 0000000..be44f75 --- /dev/null +++ b/src/main/java/ru/simsonic/rscPermissions/API/PlayerType.java @@ -0,0 +1,113 @@ +package ru.simsonic.rscPermissions.API; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +public enum PlayerType +{ + name(0), // 16 chars max + hyphenatedUUID(1), // 550e8400-e29b-41d4-a716-446655440000 + dehyphenatedUUID(2), // 550e8400e29b41d4a716446655440000 + internetWildcard(3), // 192.168.*.* + internetSubnetMask(4), // 192.168.1.0/16 + inapplicable(-1); + private final int value; + private PlayerType(int value) + { + this.value = value; + } + public static PlayerType byValue(int value) + { + for(PlayerType constant : PlayerType.values()) + if(constant.value == value) + return constant; + return inapplicable; + } + private static final Pattern nicknameRegExp = Pattern.compile("^[a-zA-Z0-9_-]{3,16}$"); + private static final Pattern hyphenatedRegExp = Pattern.compile("^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$"); + private static final Pattern dehyphenatedRegExp = Pattern.compile("^[0-9a-f]{32}$"); + private static final Pattern ipWildcardRegExp = Pattern.compile("^" + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5]|\\*)\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5]|\\*)\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5]|\\*)\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5]|\\*)$"); + private static final Pattern ipSubnetMaskRegExp = Pattern.compile("^" + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])\\." + + "([0-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])" + + "(?:/([0-9]|[1-2][0-9]|3[0-2]))$"); + public static PlayerType scanPlayerEntity(String entity) + { + if("".equals(entity)) + return name; + if(nicknameRegExp.matcher(entity).matches()) + return name; + if(hyphenatedRegExp.matcher(entity.toLowerCase()).matches()) + return hyphenatedUUID; + if(dehyphenatedRegExp.matcher(entity.toLowerCase()).matches()) + return dehyphenatedUUID; + final Matcher mIP1 = ipWildcardRegExp.matcher(entity); + if(mIP1.matches()) + { + final String a1 = mIP1.group(1); + final String a2 = mIP1.group(2); + final String a3 = mIP1.group(3); + final String a4 = mIP1.group(4); + // TO DO + long address = 0, mask = 0; + } + final Matcher mIP2 = ipSubnetMaskRegExp.matcher(entity); + if(mIP2.matches()) + { + final String a1 = mIP1.group(1); + final String a2 = mIP1.group(2); + final String a3 = mIP1.group(3); + final String a4 = mIP1.group(4); + final String sn = mIP1.group(5); + // TO DO + long address = 0, mask = 0; + } + return inapplicable; + } + public static void getAddressDetails(String entity, RowPermission row) + { + final Matcher mIP1 = ipWildcardRegExp.matcher(entity); + if(mIP1.matches()) + { + final String a1 = mIP1.group(1); + final String a2 = mIP1.group(2); + final String a3 = mIP1.group(3); + final String a4 = mIP1.group(4); + // TO DO + if("*".equals(a1)) + { + } else { + } + long address = 0, mask = 0; + } + final Matcher mIP2 = ipSubnetMaskRegExp.matcher(entity); + if(mIP2.matches()) + { + final String a1 = mIP1.group(1); + final String a2 = mIP1.group(2); + final String a3 = mIP1.group(3); + final String a4 = mIP1.group(4); + final String sn = mIP1.group(5); + // TO DO + long address = 0, mask = 0; + } + } + public boolean isEntityApplicable(String entity, String identifier) + { + switch(this) + { + case name: + return entity.equals(identifier); + case hyphenatedUUID: + identifier = identifier.replace("-", "").toLowerCase(); + case dehyphenatedUUID: + return entity.equals(identifier); + } + return false; + } +} diff --git a/src/main/java/ru/simsonic/rscPermissions/API/RowEntity.java b/src/main/java/ru/simsonic/rscPermissions/API/RowEntity.java index aa80ce3..1731a96 100644 --- a/src/main/java/ru/simsonic/rscPermissions/API/RowEntity.java +++ b/src/main/java/ru/simsonic/rscPermissions/API/RowEntity.java @@ -9,6 +9,9 @@ public class RowEntity implements Cloneable public String prefix; public String suffix; public Timestamp lifetime; + public transient PlayerType playerType; + public transient RowPermission[] permissions; + public transient RowInheritance[] inheritance; @Override public RowEntity clone() throws CloneNotSupportedException { diff --git a/src/main/java/ru/simsonic/rscPermissions/API/RowInheritance.java b/src/main/java/ru/simsonic/rscPermissions/API/RowInheritance.java index 66a27bb..197c765 100644 --- a/src/main/java/ru/simsonic/rscPermissions/API/RowInheritance.java +++ b/src/main/java/ru/simsonic/rscPermissions/API/RowInheritance.java @@ -14,7 +14,8 @@ public class RowInheritance implements Cloneable, Comparable public Destination destination; public int expirience; public Timestamp lifetime; - public transient String destinationSource; + public transient PlayerType playerType; + public transient String destinationSource; public void deriveInstance() { if(parent != null) @@ -39,4 +40,20 @@ public class RowInheritance implements Cloneable, Comparable { return (priority != t.priority) ? priority - t.priority : parent.compareTo(t.parent); } + public boolean isEntityApplicable(String identifier) + { + if(EntityType.group.equals(childType)) + return entity.equalsIgnoreCase(identifier); + switch(playerType) + { + case name: + return entity.equals(identifier); + case hyphenatedUUID: + identifier = identifier.replace("-", ""); + case dehyphenatedUUID: + return entity.equals(identifier); + } + // TO DO + return false; + } } diff --git a/src/main/java/ru/simsonic/rscPermissions/API/RowPermission.java b/src/main/java/ru/simsonic/rscPermissions/API/RowPermission.java index e0262ff..31225d1 100644 --- a/src/main/java/ru/simsonic/rscPermissions/API/RowPermission.java +++ b/src/main/java/ru/simsonic/rscPermissions/API/RowPermission.java @@ -11,10 +11,18 @@ public class RowPermission implements Cloneable public Destination destination; public int expirience; public Timestamp lifetime; - public transient String destinationSource; + public transient PlayerType playerType; + public transient String destinationSource; @Override public RowPermission clone() throws CloneNotSupportedException { return (RowPermission)super.clone(); } + public boolean isEntityApplicable(String identifier) + { + if(EntityType.group.equals(entityType)) + return entity.equalsIgnoreCase(identifier); + // TO DO + return false; + } } diff --git a/src/main/java/ru/simsonic/rscPermissions/Backends/DatabaseContents.java b/src/main/java/ru/simsonic/rscPermissions/Backends/DatabaseContents.java index 3519047..6ca0b55 100644 --- a/src/main/java/ru/simsonic/rscPermissions/Backends/DatabaseContents.java +++ b/src/main/java/ru/simsonic/rscPermissions/Backends/DatabaseContents.java @@ -1,5 +1,6 @@ package ru.simsonic.rscPermissions.Backends; import java.util.ArrayList; +import java.util.Date; import ru.simsonic.rscPermissions.API.Destination; import ru.simsonic.rscPermissions.API.RowEntity; import ru.simsonic.rscPermissions.API.RowInheritance; @@ -85,6 +86,32 @@ public class DatabaseContents inheritance = li.toArray(new RowInheritance[li.size()]); return this; } + public DatabaseContents filterLifetime() + { + if(entities == null) + entities = new RowEntity[] {}; + if(permissions == null) + permissions = new RowPermission[] {}; + if(inheritance == null) + inheritance = new RowInheritance[] {}; + final Date date = new Date(); + final ArrayList le = new ArrayList<>(); + final ArrayList lp = new ArrayList<>(); + final ArrayList li = new ArrayList<>(); + for(RowEntity row : entities) + if(!(row.lifetime != null && row.lifetime.after(date))) + le.add(row); + for(RowPermission row : permissions) + if(!(row.lifetime != null && row.lifetime.after(date))) + lp.add(row); + for(RowInheritance row : inheritance) + if(!(row.lifetime != null && row.lifetime.after(date))) + li.add(row); + entities = le.toArray(new RowEntity[le.size()]); + permissions = lp.toArray(new RowPermission[lp.size()]); + inheritance = li.toArray(new RowInheritance[li.size()]); + return this; + } public DatabaseContents filterServerId(String serverId) { if(permissions == null) diff --git a/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitEventListener.java b/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitEventListener.java index 27cec83..5a8f830 100644 --- a/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitEventListener.java +++ b/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitEventListener.java @@ -1,4 +1,5 @@ package ru.simsonic.rscPermissions.Bukkit; +import java.util.ArrayList; import org.bukkit.Bukkit; import org.bukkit.entity.Player; import org.bukkit.event.EventHandler; @@ -25,12 +26,20 @@ public class BukkitEventListener implements Listener @EventHandler public void onPlayerAsyncPreLogin(AsyncPlayerPreLoginEvent event) { - final ResolutionResult resolution = rscp.internalCache.resolvePlayer(new String[] + final ArrayList identifiers = new ArrayList<>(); + try { - event.getName(), - event.getUniqueId().toString(), - event.getAddress().getHostAddress(), - }, rscp.getServer().getServerId()); + identifiers.add(event.getName()); + } catch(RuntimeException | NoSuchMethodError ex) { + } + try + { + identifiers.add(event.getUniqueId().toString().toLowerCase()); + } catch(RuntimeException | NoSuchMethodError ex) { + } + identifiers.add(event.getAddress().getHostAddress()); + // Resolution + final ResolutionResult resolution = rscp.internalCache.resolvePlayer(identifiers.toArray(new String[identifiers.size()])); processMaintenanceLogin(event, resolution); } @EventHandler(priority = EventPriority.LOWEST) diff --git a/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitPermissionManager.java b/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitPermissionManager.java index e4e5315..6818bad 100644 --- a/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitPermissionManager.java +++ b/src/main/java/ru/simsonic/rscPermissions/Bukkit/BukkitPermissionManager.java @@ -117,31 +117,23 @@ public class BukkitPermissionManager extends RestartableThread } else params.destRegions = new String[] {}; params.destWorld = player.getLocation().getWorld().getName(); - params.destServerId = rscp.getServer().getServerId(); params.expirience = player.getLevel(); return rscp.internalCache.resolvePlayer(params); } private static String[] getPlayerIdentifiers(Player player) { final ArrayList result = new ArrayList<>(); - // For old servers Player's name can be used as entity name try { - // minecraft <= 1.7.x result.add(player.getName()); } catch(RuntimeException | NoSuchMethodError ex) { - // minecraft >= 1.8 } - // For newest servers Player's UUID is used as entity name try { - // minecraft >= 1.8 result.add(player.getUniqueId().toString().toLowerCase()); } catch(RuntimeException | NoSuchMethodError ex) { - // minecraft <= 1.7.x } - // IP address of a Player can be used as entity name too - InetSocketAddress socketAddress = player.getAddress(); + final InetSocketAddress socketAddress = player.getAddress(); if(socketAddress != null) result.add(socketAddress.getAddress().getHostAddress()); return result.toArray(new String[result.size()]); diff --git a/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultChat.java b/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultChat.java index 319a7d8..b7f0a62 100644 --- a/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultChat.java +++ b/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultChat.java @@ -1,5 +1,4 @@ package ru.simsonic.rscPermissions.Bukkit; -import net.milkbowl.vault.permission.Permission; import org.bukkit.OfflinePlayer; import org.bukkit.World; import org.bukkit.entity.Player; @@ -8,7 +7,7 @@ import ru.simsonic.rscPermissions.API.BridgeForBukkitAPI; public final class VaultChat extends net.milkbowl.vault.chat.Chat { private final BridgeForBukkitAPI bridge; - public VaultChat(BridgeForBukkitAPI bridge, Permission perms) + public VaultChat(BridgeForBukkitAPI bridge, net.milkbowl.vault.permission.Permission perms) { super(perms); this.bridge = bridge; @@ -16,12 +15,12 @@ public final class VaultChat extends net.milkbowl.vault.chat.Chat @Override public String getName() { - throw new UnsupportedOperationException("This method is still unsupported. Sorry."); + return bridge.getName(); } @Override public boolean isEnabled() { - throw new UnsupportedOperationException("This method is still unsupported. Sorry."); + return bridge.isEnabled(); } @Override public String getPlayerPrefix(String world, String player) diff --git a/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultPermission.java b/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultPermission.java index 70ec805..d7bfab4 100644 --- a/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultPermission.java +++ b/src/main/java/ru/simsonic/rscPermissions/Bukkit/VaultPermission.java @@ -15,17 +15,17 @@ public class VaultPermission extends net.milkbowl.vault.permission.Permission @Override public String getName() { - throw new UnsupportedOperationException("This method is still unsupported. Sorry."); + return bridge.getName(); } @Override public boolean isEnabled() { - throw new UnsupportedOperationException("This method is still unsupported. Sorry."); + return bridge.isEnabled(); } @Override public boolean hasSuperPermsCompat() { - throw new UnsupportedOperationException("This method is still unsupported. Sorry."); + return true; } @Override public boolean playerHas(String world, String player, String permission) diff --git a/src/main/java/ru/simsonic/rscPermissions/BukkitPluginMain.java b/src/main/java/ru/simsonic/rscPermissions/BukkitPluginMain.java index be7d734..4e0ff33 100644 --- a/src/main/java/ru/simsonic/rscPermissions/BukkitPluginMain.java +++ b/src/main/java/ru/simsonic/rscPermissions/BukkitPluginMain.java @@ -57,7 +57,7 @@ public final class BukkitPluginMain extends JavaPlugin // Restore temporary cached data from json files internalCache.setDefaultGroup(settings.getDefaultGroup()); final DatabaseContents contents = fileCache.retrieveContents(); - contents.filterServerId(getServer().getServerId()); + contents.filterServerId(getServer().getServerId()).filterLifetime(); internalCache.fill(contents); consoleLog.log(Level.INFO, "[rscp] Loaded {0} entity, {1} permission and {2} inheritance rows from local cache.", new Integer[] diff --git a/src/main/java/ru/simsonic/rscPermissions/IndependentMain.java b/src/main/java/ru/simsonic/rscPermissions/IndependentMain.java index c8af30c..0274a91 100644 --- a/src/main/java/ru/simsonic/rscPermissions/IndependentMain.java +++ b/src/main/java/ru/simsonic/rscPermissions/IndependentMain.java @@ -33,7 +33,7 @@ public class IndependentMain System.out.println("Loading permissions from json files."); final DatabaseContents contents = localJsn.retrieveContents(); System.out.println("Filter and calculating permission tree."); - contents.filterServerId("localtest"); + contents.filterServerId("localtest").filterLifetime(); intCache.fill(contents); System.out.println("Done."); } diff --git a/src/main/java/ru/simsonic/rscPermissions/InternalCache/InternalCache.java b/src/main/java/ru/simsonic/rscPermissions/InternalCache/InternalCache.java index 1d2f900..474b13e 100644 --- a/src/main/java/ru/simsonic/rscPermissions/InternalCache/InternalCache.java +++ b/src/main/java/ru/simsonic/rscPermissions/InternalCache/InternalCache.java @@ -1,9 +1,12 @@ package ru.simsonic.rscPermissions.InternalCache; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; +import java.util.Map.Entry; import ru.simsonic.rscPermissions.API.EntityType; +import ru.simsonic.rscPermissions.API.PlayerType; import ru.simsonic.rscPermissions.API.RowEntity; import ru.simsonic.rscPermissions.API.RowInheritance; import ru.simsonic.rscPermissions.API.RowPermission; @@ -19,55 +22,160 @@ public class InternalCache defaultInheritance.deriveInstance(); } private final HashMap entities_g = new HashMap<>(); - private final HashMap entities_u = new HashMap<>(); + private final HashMap entities_u = new HashMap<>();/* private final ArrayList permissions_p2g = new ArrayList<>(); private final ArrayList permissions_p2u = new ArrayList<>(); private final ArrayList inheritance_g2g = new ArrayList<>(); - private final ArrayList inheritance_g2u = new ArrayList<>(); - public static class InheritanceLeaf implements Comparable - { - public RowInheritance node; - public String instantiator; - public InheritanceLeaf[] subleafs; - public String prefix; - public String suffix; - @Override - public int compareTo(InheritanceLeaf other) + private final ArrayList inheritance_g2u = new ArrayList<>();*/ + public synchronized void fill(DatabaseContents contents) + { + clear(); + // Import data + importEntities(contents); + importPermissions(contents.permissions); + importInheritance(contents.inheritance); + // Parse PlayerType's + for(RowEntity row : entities_u.values()) + row.playerType = PlayerType.scanPlayerEntity(row.entity); + } + private void importEntities(DatabaseContents contents) + { + final HashSet names_u = new HashSet<>(); + final HashSet names_g = new HashSet<>(); + for(RowEntity row : contents.entities) + if(row.entityType == EntityType.group) + { + entities_g.put(row.entity.toLowerCase(), row); + names_g.add(row.entity.toLowerCase()); + } else { + entities_u.put(row.entity, row); + names_u.add(row.entity); + } + for(RowPermission row : contents.permissions) + if(row.entityType == EntityType.group) + names_g.add(row.entity.toLowerCase()); + else + names_u.add(row.entity); + for(RowInheritance row : contents.inheritance) { - return (other.node != null && node != null) ? other.node.compareTo(node) : 0; + names_g.add(row.parent.toLowerCase()); + if(row.childType == EntityType.group) + names_g.add(row.entity.toLowerCase()); + else + names_u.add(row.entity); } + for(String name : names_g) + if(!entities_g.containsKey(name)) + entities_g.put(name, new RowEntity()); + for(String name : names_u) + if(!entities_u.containsKey(name)) + entities_u.put(name, new RowEntity()); } - private final HashMap entityTrees = new HashMap<>(); - private final HashMap permissionsTreesG = new HashMap<>(); - private final HashMap permissionsTreesU = new HashMap<>(); - private final HashMap inheritanceTreesG = new HashMap<>(); - private final HashMap inheritanceTreesU = new HashMap<>(); - public synchronized void fill(DatabaseContents contents) + private void importPermissions(RowPermission[] rows) { - clear(); - if(contents.entities != null) - importEntities(contents.entities); - if(contents.permissions != null) - importPermissions(contents.permissions); - if(contents.inheritance != null) - importInheritance(contents.inheritance); - buildInheritanceForest(); + final ArrayList permissions_p2g = new ArrayList<>(); + final ArrayList permissions_p2u = new ArrayList<>(); + for(RowPermission row : rows) + if(row.entityType == EntityType.group) + permissions_p2g.add(row); + else + permissions_p2u.add(row); + for(String entry : entities_g.keySet()) + { + final ArrayList permissions = new ArrayList<>(); + for(RowPermission row : permissions_p2g) + if(row.entity.toLowerCase().equals(entry)) + permissions.add(row); + entities_g.get(entry).permissions = permissions.toArray(new RowPermission[permissions.size()]); + } + for(String entry : entities_u.keySet()) + { + final ArrayList permissions = new ArrayList<>(); + for(RowPermission row : permissions_p2u) + if(row.entity.equals(entry)) + permissions.add(row); + entities_u.get(entry).permissions = permissions.toArray(new RowPermission[permissions.size()]); + } + } + private void importInheritance(RowInheritance[] rows) + { + final ArrayList inheritance_g2g = new ArrayList<>(); + final ArrayList inheritance_g2u = new ArrayList<>(); + for(RowInheritance row : rows) + if(row.childType == EntityType.group) + inheritance_g2g.add(row); + else + inheritance_g2u.add(row); + for(Entry entry : entities_g.entrySet()) + { + final ArrayList inheritances = new ArrayList<>(); + final String name = entry.getKey(); + for(RowInheritance row : inheritance_g2g) + if(row.entity.toLowerCase().equals(name)) + inheritances.add(row); + entry.getValue().inheritance = inheritances.toArray(new RowInheritance[inheritances.size()]); + } + for(Entry entry : entities_u.entrySet()) + { + final ArrayList inheritance = new ArrayList<>(); + final String name = entry.getKey(); + for(RowInheritance row : inheritance_g2u) + if(row.entity.equals(name)) + inheritance.add(row); + entry.getValue().inheritance = inheritance.toArray(new RowInheritance[inheritance.size()]); + } } - public synchronized ResolutionResult resolvePlayer(String player, String serverId) + public synchronized ResolutionResult resolvePlayer(String player) { - return resolvePlayer(new String[] { player }, serverId); + return resolvePlayer(new String[] { player }); } - public synchronized ResolutionResult resolvePlayer(String[] player, String serverId) + public synchronized ResolutionResult resolvePlayer(String[] player) { final ResolutionParams params = new ResolutionParams(); params.applicableIdentifiers = player; params.destRegions = new String[] {}; // params.destWorld = ""; - params.destServerId = serverId; // params.expirience = 0; return resolvePlayer(params); } public synchronized ResolutionResult resolvePlayer(ResolutionParams params) + { + final ArrayList intermediate = new ArrayList<>(); + if(entities_g.containsKey("")) + { + params.parentEntity = entities_g.get(""); + params.instantiator = ""; + intermediate.add(resolveParent(params)); + } + for(RowEntity row : entities_u.values()) + for(String identifier : params.applicableIdentifiers) + if(row.playerType.isEntityApplicable(row.entity, identifier)) + { + params.parentEntity = row; + params.instantiator = ""; + intermediate.add(resolveParent(params)); + break; + } + final ResolutionResult result = processResultColumn(params, intermediate); + + parents.addAll(Arrays.asList(implicitInheritance_u)); + parents.add(defaultInheritance); + for(Entry entity : inheritanceTrees_u.entrySet()) + { + for(RowInheritance row : entity.getValue()) + if(PlayerType.isEntityApplicable(entity, , entity)) + }; + final ResolutionResult result = new ResolutionResult(); + intermediate.addAll(Arrays.asList(implicitPermissions_u)); + final ArrayList inheritance = new ArrayList<>(); + return result; + } + public synchronized ResolutionResult resolveParent(ResolutionParams params) + { + return null; + } + /* + public synchronized ResolutionResult resolvePlayerOld(ResolutionParams params) { final ArrayList applicableBranches = new ArrayList<>(); // Grab all inheritance rows applicable to this player @@ -85,34 +193,6 @@ public class InternalCache intermediateResults.clear(); return result; } - private void importEntities(RowEntity[] rows) - { - for(RowEntity row : rows) - { - if(row.entityType == EntityType.group) - entities_g.put(row.entity.toLowerCase(), row); - else - entities_u.put(row.entity.toLowerCase(), row); - } - } - private void importPermissions(RowPermission[] rows) - { - for(RowPermission row : rows) - { - if(row.entityType == EntityType.group) - permissions_p2g.add(row); - else - permissions_p2u.add(row); - } - } - private void importInheritance(RowInheritance[] rows) - { - for(RowInheritance row : rows) - if(row.childType == EntityType.group) - inheritance_g2g.add(row); - else - inheritance_g2u.add(row); - } // FROM HERE I SHOULD MAKE IT WORKING private void buildInheritanceForest() { @@ -143,7 +223,7 @@ public class InternalCache } final ArrayList parents = new ArrayList<>(); for(RowInheritance row : inheritance_g2g) - if(row.parent.equalsIgnoreCase(source.entity)) + if(row.parentEntity.equalsIgnoreCase(source.entity)) parents.add(row); Collections.sort(parents); final ArrayList subleafs = new ArrayList<>(); @@ -152,7 +232,7 @@ public class InternalCache result.subleafs = subleafs.toArray(new InheritanceLeaf[subleafs.size()]); return result; } - private ResolutionResult resolveBranch(ResolutionParams params, InheritanceLeaf branch, String instantiator) + private ResolutionResult resolveBranch(ResolutionParams params, RowInheritance[] rows, String instantiator) { final ArrayList intermediateResults = new ArrayList<>(); for(InheritanceLeaf subleaf : branch.subleafs) @@ -166,31 +246,32 @@ public class InternalCache intermediateResults.clear(); return result; } - private ResolutionResult processResultColumn(ResolutionParams params, ArrayList resultList, String instantiator) + */ + private ResolutionResult processResultColumn(ResolutionParams params, ArrayList intermediate) { - switch(resultList.size()) + switch(intermediate.size()) { case 0: return new ResolutionResult(); case 1: - return resultList.get(0); + return intermediate.get(0); default: final ResolutionResult result = new ResolutionResult(); final ArrayList permissions = new ArrayList<>(); result.prefix = ""; result.suffix = ""; - for(ResolutionResult intermediate : resultList) + for(ResolutionResult oneOf : intermediate) { // Prefixes & suffixes - if(intermediate.prefix != null && !"".equals(intermediate.prefix)) - result.prefix = result.prefix.replace("%", result.prefix); - if(intermediate.suffix != null && !"".equals(intermediate.suffix)) - result.suffix = result.suffix.replace("%", result.suffix); - result.prefix = result.prefix.replace(Settings.instantiator, instantiator); - result.suffix = result.suffix.replace(Settings.instantiator, instantiator); + if(oneOf.prefix != null && !"".equals(oneOf.prefix)) + result.prefix = result.prefix.replace("%", oneOf.prefix); + if(oneOf.suffix != null && !"".equals(oneOf.suffix)) + result.suffix = result.suffix.replace("%", oneOf.suffix); + result.prefix = result.prefix.replace(Settings.instantiator, params.instantiator); + result.suffix = result.suffix.replace(Settings.instantiator, params.instantiator); // Permissions - for(RowPermission permission : intermediate.permissions) - if(isPermissionApplicable(params, permission, instantiator)) + for(RowPermission permission : oneOf.permissions) + if(isPermissionApplicable(params, permission, params.instantiator)) permissions.add(permission); } result.permissions = permissions.toArray(new RowPermission[permissions.size()]); @@ -217,9 +298,11 @@ public class InternalCache { entities_g.clear(); entities_u.clear(); + /* permissions_p2g.clear(); permissions_p2u.clear(); inheritance_g2g.clear(); inheritance_g2u.clear(); + */ } } diff --git a/src/main/java/ru/simsonic/rscPermissions/InternalCache/ResolutionParams.java b/src/main/java/ru/simsonic/rscPermissions/InternalCache/ResolutionParams.java index 29f0582..0bef1a5 100644 --- a/src/main/java/ru/simsonic/rscPermissions/InternalCache/ResolutionParams.java +++ b/src/main/java/ru/simsonic/rscPermissions/InternalCache/ResolutionParams.java @@ -1,10 +1,12 @@ package ru.simsonic.rscPermissions.InternalCache; +import ru.simsonic.rscPermissions.API.RowEntity; public class ResolutionParams { public String[] applicableIdentifiers; public String[] destRegions; public String destWorld; - public String destServerId; public int expirience; + protected transient RowEntity parentEntity; + protected transient String instantiator; }