Implement optional permission check method for commands
This allows plugins to customize which players can use their commands. For players without permission, the command is effectively invisible, and the handling is passed through to the backend server.
This commit is contained in:
@@ -8,6 +8,7 @@ import com.velocitypowered.api.command.CommandSource;
|
||||
import com.velocitypowered.api.event.EventManager;
|
||||
import com.velocitypowered.api.event.proxy.ProxyInitializeEvent;
|
||||
import com.velocitypowered.api.event.proxy.ProxyShutdownEvent;
|
||||
import com.velocitypowered.api.permission.Tristate;
|
||||
import com.velocitypowered.api.plugin.PluginManager;
|
||||
import com.velocitypowered.api.proxy.Player;
|
||||
import com.velocitypowered.api.proxy.ProxyServer;
|
||||
@@ -39,6 +40,7 @@ import net.kyori.text.serializer.ComponentSerializers;
|
||||
import net.kyori.text.serializer.GsonComponentSerializer;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
|
||||
import java.net.InetSocketAddress;
|
||||
import java.nio.file.Files;
|
||||
@@ -77,8 +79,8 @@ public class VelocityServer implements ProxyServer {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(String permission) {
|
||||
return true;
|
||||
public @NonNull Tristate getPermissionValue(@NonNull String permission) {
|
||||
return Tristate.TRUE;
|
||||
}
|
||||
};
|
||||
private Ratelimiter ipAttemptLimiter;
|
||||
|
@@ -3,6 +3,7 @@ package com.velocitypowered.proxy.command;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.velocitypowered.api.command.Command;
|
||||
import com.velocitypowered.api.command.CommandSource;
|
||||
import com.velocitypowered.api.permission.Tristate;
|
||||
import com.velocitypowered.api.proxy.Player;
|
||||
import com.velocitypowered.api.proxy.ProxyServer;
|
||||
import com.velocitypowered.api.proxy.ServerConnection;
|
||||
@@ -12,6 +13,7 @@ import net.kyori.text.TextComponent;
|
||||
import net.kyori.text.event.ClickEvent;
|
||||
import net.kyori.text.event.HoverEvent;
|
||||
import net.kyori.text.format.TextColor;
|
||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
@@ -88,4 +90,9 @@ public class ServerCommand implements Command {
|
||||
return ImmutableList.of();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(@NonNull CommandSource source, @NonNull String[] args) {
|
||||
return source.getPermissionValue("velocity.command.server") != Tristate.FALSE;
|
||||
}
|
||||
}
|
||||
|
@@ -5,6 +5,7 @@ import com.velocitypowered.api.command.CommandSource;
|
||||
import com.velocitypowered.proxy.VelocityServer;
|
||||
import net.kyori.text.TextComponent;
|
||||
import net.kyori.text.format.TextColor;
|
||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
|
||||
public class ShutdownCommand implements Command {
|
||||
private final VelocityServer server;
|
||||
@@ -21,4 +22,9 @@ public class ShutdownCommand implements Command {
|
||||
}
|
||||
server.shutdown();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(@NonNull CommandSource source, @NonNull String[] args) {
|
||||
return source == server.getConsoleCommandSource();
|
||||
}
|
||||
}
|
||||
|
@@ -2,10 +2,12 @@ package com.velocitypowered.proxy.command;
|
||||
|
||||
import com.velocitypowered.api.command.Command;
|
||||
import com.velocitypowered.api.command.CommandSource;
|
||||
import com.velocitypowered.api.permission.Tristate;
|
||||
import com.velocitypowered.proxy.VelocityServer;
|
||||
import net.kyori.text.TextComponent;
|
||||
import net.kyori.text.event.ClickEvent;
|
||||
import net.kyori.text.format.TextColor;
|
||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
|
||||
public class VelocityCommand implements Command {
|
||||
@Override
|
||||
@@ -37,4 +39,9 @@ public class VelocityCommand implements Command {
|
||||
source.sendMessage(velocityInfo);
|
||||
source.sendMessage(velocityWebsite);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(@NonNull CommandSource source, @NonNull String[] args) {
|
||||
return source.getPermissionValue("velocity.command.info") != Tristate.FALSE;
|
||||
}
|
||||
}
|
||||
|
@@ -46,6 +46,10 @@ public class VelocityCommandManager implements CommandManager {
|
||||
}
|
||||
|
||||
try {
|
||||
if (!command.hasPermission(source, actualArgs)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
command.execute(source, actualArgs);
|
||||
return true;
|
||||
} catch (Exception e) {
|
||||
@@ -62,24 +66,29 @@ public class VelocityCommandManager implements CommandManager {
|
||||
return Optional.empty();
|
||||
}
|
||||
|
||||
String command = split[0];
|
||||
String alias = split[0];
|
||||
if (split.length == 1) {
|
||||
return Optional.of(commands.keySet().stream()
|
||||
.filter(cmd -> cmd.regionMatches(true, 0, command, 0, command.length()))
|
||||
.map(cmd -> "/" + cmd)
|
||||
return Optional.of(commands.entrySet().stream()
|
||||
.filter(ent -> ent.getKey().regionMatches(true, 0, alias, 0, alias.length()))
|
||||
.filter(ent -> ent.getValue().hasPermission(source, new String[0]))
|
||||
.map(ent -> "/" + ent.getKey())
|
||||
.collect(Collectors.toList()));
|
||||
}
|
||||
|
||||
String[] actualArgs = Arrays.copyOfRange(split, 1, split.length);
|
||||
Command executor = commands.get(command);
|
||||
if (executor == null) {
|
||||
Command command = commands.get(alias.toLowerCase(Locale.ENGLISH));
|
||||
if (command == null) {
|
||||
return Optional.empty();
|
||||
}
|
||||
|
||||
try {
|
||||
return Optional.of(executor.suggest(source, actualArgs));
|
||||
if (!command.hasPermission(source, actualArgs)) {
|
||||
return Optional.empty();
|
||||
}
|
||||
|
||||
return Optional.of(command.suggest(source, actualArgs));
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("Unable to invoke suggestions for command " + command + " for " + source, e);
|
||||
throw new RuntimeException("Unable to invoke suggestions for command " + alias + " for " + source, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -7,6 +7,7 @@ import com.velocitypowered.api.event.player.PlayerSettingsChangedEvent;
|
||||
import com.velocitypowered.api.event.player.ServerPreConnectEvent;
|
||||
import com.velocitypowered.api.permission.PermissionFunction;
|
||||
import com.velocitypowered.api.permission.PermissionProvider;
|
||||
import com.velocitypowered.api.permission.Tristate;
|
||||
import com.velocitypowered.api.proxy.ConnectionRequestBuilder;
|
||||
import com.velocitypowered.api.proxy.Player;
|
||||
import com.velocitypowered.api.proxy.ServerConnection;
|
||||
@@ -335,8 +336,8 @@ public class ConnectedPlayer implements MinecraftConnectionAssociation, Player {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(String permission) {
|
||||
return permissionFunction.getPermissionSetting(permission).asBoolean();
|
||||
public @NonNull Tristate getPermissionValue(@NonNull String permission) {
|
||||
return permissionFunction.getPermissionValue(permission);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
Reference in New Issue
Block a user