From 5dad9e0c54807c24b463979c17ecfb6d3f1f4937 Mon Sep 17 00:00:00 2001 From: Intybyte Date: Sat, 8 Feb 2025 16:19:25 +0100 Subject: [PATCH 1/5] Add pipe OR handling for permissions --- .../co/aikar/commands/CommandManager.java | 26 ++++++++++++++++--- 1 file changed, 22 insertions(+), 4 deletions(-) diff --git a/core/src/main/java/co/aikar/commands/CommandManager.java b/core/src/main/java/co/aikar/commands/CommandManager.java index 4eb16e2b..e541b6ee 100644 --- a/core/src/main/java/co/aikar/commands/CommandManager.java +++ b/core/src/main/java/co/aikar/commands/CommandManager.java @@ -329,12 +329,30 @@ public abstract class CommandManager< if (permission == null || permission.isEmpty()) { return true; } - for (String perm : ACFPatterns.COMMA.split(permission)) { - if (!perm.isEmpty() && !issuer.hasPermission(perm)) { - return false; + + //handle commas as an AND operation + if (permission.contains(",")) { + for (String perm : ACFPatterns.COMMA.split(permission)) { + if (!perm.isEmpty() && !issuer.hasPermission(perm)) { + return false; + } } + return true; } - return true; + + //handle pipe as an OR operation + if (permission.contains("|")) { + for (String perm : ACFPatterns.PIPE.split(permission)) { + perm = perm.trim(); + if (!perm.isEmpty() && issuer.hasPermission(perm)) { + return true; + } + } + return false; + } + + //if none are used just test the permission itself + return issuer.hasPermission(permission); } public synchronized RootCommand getRootCommand(@NotNull String cmd) { From 0e5e662c1a3a7385cda49037d00f9a4c319397b9 Mon Sep 17 00:00:00 2001 From: Intybyte Date: Sat, 8 Feb 2025 16:21:07 +0100 Subject: [PATCH 2/5] Unnecessary trim --- core/src/main/java/co/aikar/commands/CommandManager.java | 1 - 1 file changed, 1 deletion(-) diff --git a/core/src/main/java/co/aikar/commands/CommandManager.java b/core/src/main/java/co/aikar/commands/CommandManager.java index e541b6ee..6dccfe64 100644 --- a/core/src/main/java/co/aikar/commands/CommandManager.java +++ b/core/src/main/java/co/aikar/commands/CommandManager.java @@ -343,7 +343,6 @@ public abstract class CommandManager< //handle pipe as an OR operation if (permission.contains("|")) { for (String perm : ACFPatterns.PIPE.split(permission)) { - perm = perm.trim(); if (!perm.isEmpty() && issuer.hasPermission(perm)) { return true; } From c057b14f6c14f93b96fa0e953e1625f4ea34139a Mon Sep 17 00:00:00 2001 From: Intybyte Date: Tue, 4 Mar 2025 18:15:11 +0100 Subject: [PATCH 3/5] Composition over inheritance for looser coupling --- .../java/co/aikar/commands/ACFSpongeUtil.java | 2 +- .../aikar/commands/SpongeCommandContexts.java | 2 +- .../aikar/commands/SpongeCommandIssuer.java | 6 +- .../aikar/commands/SpongeCommandSource.java | 74 +++---------------- 4 files changed, 16 insertions(+), 68 deletions(-) diff --git a/sponge10/src/main/java/co/aikar/commands/ACFSpongeUtil.java b/sponge10/src/main/java/co/aikar/commands/ACFSpongeUtil.java index 43fbf509..08c27cc5 100644 --- a/sponge10/src/main/java/co/aikar/commands/ACFSpongeUtil.java +++ b/sponge10/src/main/java/co/aikar/commands/ACFSpongeUtil.java @@ -56,7 +56,7 @@ public class ACFSpongeUtil { while (iter.hasNext()) { Player player = iter.next(); if (requester instanceof Player && !((Player) requester).canSee(player)) { - if (requester.hasPermission("acf.seevanish")) { + if (requester.commandCause().hasPermission("acf.seevanish")) { if (!search.endsWith(":confirm")) { confirmList.add(player); iter.remove(); diff --git a/sponge10/src/main/java/co/aikar/commands/SpongeCommandContexts.java b/sponge10/src/main/java/co/aikar/commands/SpongeCommandContexts.java index 062c33a4..1d543a1a 100644 --- a/sponge10/src/main/java/co/aikar/commands/SpongeCommandContexts.java +++ b/sponge10/src/main/java/co/aikar/commands/SpongeCommandContexts.java @@ -132,7 +132,7 @@ public class SpongeCommandContexts extends CommandContexts context.getSource().commandCause()); registerIssuerAwareContext(SpongeCommandSource.class, SpongeCommandExecutionContext::getSource); registerIssuerAwareContext(ServerPlayer.class, (c) -> { ServerPlayer serverPlayer = c.getIssuer().getServerPlayer(); diff --git a/sponge10/src/main/java/co/aikar/commands/SpongeCommandIssuer.java b/sponge10/src/main/java/co/aikar/commands/SpongeCommandIssuer.java index 32139b52..4a650727 100644 --- a/sponge10/src/main/java/co/aikar/commands/SpongeCommandIssuer.java +++ b/sponge10/src/main/java/co/aikar/commands/SpongeCommandIssuer.java @@ -64,7 +64,7 @@ public class SpongeCommandIssuer implements CommandIssuer { } //generate a unique id based of the name (like for the console command sender) - return UUID.nameUUIDFromBytes(source.identifier().getBytes(StandardCharsets.UTF_8)); + return UUID.nameUUIDFromBytes(source.commandCause().identifier().getBytes(StandardCharsets.UTF_8)); } public Player getPlayer() { @@ -83,13 +83,13 @@ public class SpongeCommandIssuer implements CommandIssuer { @Override public void sendMessageInternal(String message) { try { - source.audience().sendMessage(LegacyComponentSerializer.legacyAmpersand().deserialize(message)); + source.commandCause().audience().sendMessage(LegacyComponentSerializer.legacyAmpersand().deserialize(message)); } catch (Exception ignored) {} } @Override public boolean hasPermission(final String permission) { - return this.source.hasPermission(permission); + return this.source.commandCause().hasPermission(permission); } @Override diff --git a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java index de62c90d..6829f49c 100644 --- a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java +++ b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java @@ -1,25 +1,16 @@ package co.aikar.commands; -import net.kyori.adventure.audience.Audience; -import net.kyori.adventure.identity.Identified; -import net.kyori.adventure.identity.Identity; -import net.kyori.adventure.text.Component; -import org.spongepowered.api.block.BlockSnapshot; import org.spongepowered.api.command.CommandCause; import org.spongepowered.api.command.parameter.CommandContext; -import org.spongepowered.api.event.Cause; import org.spongepowered.api.service.permission.Subject; import org.spongepowered.api.util.locale.LocaleSource; import org.spongepowered.api.util.locale.Locales; -import org.spongepowered.api.world.server.ServerLocation; -import org.spongepowered.math.vector.Vector3d; import java.util.Locale; -import java.util.Optional; -public class SpongeCommandSource implements LocaleSource, CommandCause { - private CommandCause commandCause; - private LocaleSource localeSource; +public class SpongeCommandSource { + private final CommandCause commandCause; + private final LocaleSource localeSource; public SpongeCommandSource(CommandContext commandContext) { commandCause = commandContext.cause(); @@ -31,17 +22,15 @@ public class SpongeCommandSource implements LocaleSource, CommandCause { } } - public SpongeCommandSource(T obj) { - if (obj instanceof CommandCause) { - commandCause = (CommandCause) obj; - } - - if (obj instanceof LocaleSource) { - localeSource = (LocaleSource) obj; + public SpongeCommandSource(CommandCause cause) { + this.commandCause = cause; + if (cause instanceof LocaleSource) { + localeSource = (LocaleSource) cause; + } else { + localeSource = null; } } - @Override public Locale locale() { if (localeSource == null) { return Locales.DEFAULT; @@ -49,48 +38,7 @@ public class SpongeCommandSource implements LocaleSource, CommandCause { return localeSource.locale(); } - @Override - public Cause cause() { - return commandCause.cause(); - } - - @Override - public Subject subject() { - return commandCause.subject(); - } - - @Override - public Audience audience() { - return commandCause.audience(); - } - - @Override - public Optional location() { - return commandCause.location(); - } - - @Override - public Optional rotation() { - return commandCause.rotation(); - } - - @Override - public Optional targetBlock() { - return commandCause.targetBlock(); - } - - @Override - public void sendMessage(Component message) { - commandCause.sendMessage(message); - } - - @Override - public void sendMessage(Identified source, Component message) { - commandCause.sendMessage(source, message); - } - - @Override - public void sendMessage(Identity source, Component message) { - commandCause.sendMessage(source, message); + public CommandCause commandCause() { + return commandCause; } } From d55253c669d529d6d640be5da6ff3eb385490626 Mon Sep 17 00:00:00 2001 From: Intybyte Date: Tue, 4 Mar 2025 18:27:24 +0100 Subject: [PATCH 4/5] Remove unused constructor + extra check --- .../co/aikar/commands/SpongeCommandSource.java | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java index 6829f49c..b5ae221c 100644 --- a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java +++ b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java @@ -1,8 +1,6 @@ package co.aikar.commands; import org.spongepowered.api.command.CommandCause; -import org.spongepowered.api.command.parameter.CommandContext; -import org.spongepowered.api.service.permission.Subject; import org.spongepowered.api.util.locale.LocaleSource; import org.spongepowered.api.util.locale.Locales; @@ -12,20 +10,12 @@ public class SpongeCommandSource { private final CommandCause commandCause; private final LocaleSource localeSource; - public SpongeCommandSource(CommandContext commandContext) { - commandCause = commandContext.cause(); - Subject subject = commandContext.subject(); - if (subject instanceof LocaleSource) { - localeSource = (LocaleSource) subject; - } else { - localeSource = null; - } - } - public SpongeCommandSource(CommandCause cause) { this.commandCause = cause; if (cause instanceof LocaleSource) { localeSource = (LocaleSource) cause; + } else if (cause.subject() instanceof LocaleSource) { + localeSource = (LocaleSource) cause.subject(); } else { localeSource = null; } From 056d595ddf51f327215664f7f4a00fba166a5ec4 Mon Sep 17 00:00:00 2001 From: Intybyte Date: Mon, 24 Mar 2025 15:30:49 +0100 Subject: [PATCH 5/5] Add @NotNull annotations, restore and deprecate old constructors, only store Locale. --- .../aikar/commands/SpongeCommandSource.java | 44 ++++++++++++++----- 1 file changed, 32 insertions(+), 12 deletions(-) diff --git a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java index b5ae221c..9d876399 100644 --- a/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java +++ b/sponge10/src/main/java/co/aikar/commands/SpongeCommandSource.java @@ -1,34 +1,54 @@ package co.aikar.commands; +import org.jetbrains.annotations.NotNull; import org.spongepowered.api.command.CommandCause; +import org.spongepowered.api.command.parameter.CommandContext; import org.spongepowered.api.util.locale.LocaleSource; import org.spongepowered.api.util.locale.Locales; import java.util.Locale; public class SpongeCommandSource { - private final CommandCause commandCause; - private final LocaleSource localeSource; + private final @NotNull CommandCause commandCause; + private final @NotNull Locale locale; - public SpongeCommandSource(CommandCause cause) { + public SpongeCommandSource(@NotNull CommandCause cause) { this.commandCause = cause; if (cause instanceof LocaleSource) { - localeSource = (LocaleSource) cause; + locale = ((LocaleSource) cause).locale(); } else if (cause.subject() instanceof LocaleSource) { - localeSource = (LocaleSource) cause.subject(); + locale = ((LocaleSource) cause.subject()).locale(); } else { - localeSource = null; + locale = Locales.DEFAULT; } } - public Locale locale() { - if (localeSource == null) { - return Locales.DEFAULT; - } - return localeSource.locale(); + @Deprecated + public SpongeCommandSource(CommandContext commandContext) { + this(commandContext.cause()); } - public CommandCause commandCause() { + @Deprecated + public SpongeCommandSource(T obj) { + if (obj instanceof CommandCause) { + commandCause = (CommandCause) obj; + } else { + //having it set to null will lead to unexpected behaviour/NPEs + throw new IllegalArgumentException("When creating SpongeCommandSource the object must extend CommandCause"); + } + + if (obj instanceof LocaleSource) { + locale = ((LocaleSource) obj).locale(); + } else { + locale = Locales.DEFAULT; + } + } + + public @NotNull Locale locale() { + return locale; + } + + public @NotNull CommandCause commandCause() { return commandCause; } }