@Listener public void onModifyBlock(ChangeBlockEvent event, @First Player player) { logger.info("Call: " + event.getClass()); if (event .getCause() .get(NamedCause.NOTIFIER, Player.class) .map(p -> p.equals(player)) .orElse(false)) { logger.info("Player cause is notifier."); return; } WorldFallbackContext worldContext = worldContexts.get(event.getTargetWorld().getUniqueId()); boolean canModifyWild = Optional.ofNullable(worldContext) .flatMap(w -> w.getWilderness().getPublicPermission(MODIFY)) .orElse(MODIFY.isAllowedByDefaultOnTheWild()); Optional<Map<Vector3i, ClaimedChunk>> chunkMap = getChunkMap(event.getTargetWorld()); claimedCheck: if (chunkMap.isPresent()) { Map<Vector3i, ClaimedChunk> subMap = chunkMap.get(); Set<Vector3i> checkedChunks = new HashSet<>(2); for (Transaction<BlockSnapshot> transaction : event.getTransactions()) { Vector3i chunkPosition = blockToChunk(transaction.getOriginal().getPosition()); if (checkedChunks.contains(chunkPosition)) continue; ClaimedChunk claimedChunk = subMap.get(chunkPosition); if (claimedChunk != null && !claimedChunk.check(MODIFY, player)) { logger.info("Chunk modification cancelled: " + chunkPosition + " " + event.getCause()); event.setCancelled(true); return; } else if (!canModifyWild) break claimedCheck; checkedChunks.add(chunkPosition); logger.info("Chunk modification allowed: " + chunkPosition + " " + event); } return; } if (!canModifyWild) { if (worldContext != null) worldContext.getWilderness().notifyFailure(MODIFY, player); else MODIFY.notifyFailure(player, PlayerName.WILDERNESS); logger.info("Chunk modification cancelled because MODIFY is not allowed on unclaimed chunks"); event.setCancelled(true); } }
private WorldFallbackContext loadWorldContext(World world) throws IOException { Path worldPath = configDir.resolve("world"); Path configPath = worldPath.resolve(world.getName().replaceAll("[^a-zA-Z0-9-]", "_") + ".conf"); if (!Files.isDirectory(worldPath)) Files.createDirectory(worldPath); HoconConfigurationLoader loader = HoconConfigurationLoader.builder().setPath(configPath).build(); CommentedConfigurationNode main = loader.load( ConfigurationOptions.defaults() .setShouldCopyDefaults(true) .setHeader( "Default wild permissions on the world " + world.getName() + " with dimension " + world.getDimension().getName() + " and unique id: " + world.getUniqueId())); CommentedConfigurationNode wildPerms = main.getNode("wild-permissions"); wildPerms.setComment( "The permissions that affects unclaimed chunks on this world. Null values are inherited from the default-world-permissions declared on the default-permissions.conf file"); CommentedConfigurationNode defaultPerms = main.getNode("fallback-permissions"); defaultPerms.setComment( "The fallback permissions that will be used when a claimed chunk or a zone does not define the permission, this will take priority over the default defined on the defailt-permission.conf file"); WorldFallbackContext worldContext = new WorldFallbackContext(world.getUniqueId()); loadWorldConfig(worldContext, defaultPerms, false); loadWorldConfig(worldContext.getWilderness(), wildPerms, true); try { loader.save(main); } catch (Exception e) { logger.error( "Failed to save the world config file for " + world.getName() + " DIM:" + world.getDimension().getName(), e); } return worldContext; }