Web editor changes

This commit is contained in:
Luck 2019-11-12 12:12:53 +00:00
parent c836cce59b
commit 79c10c986e
No known key found for this signature in database
GPG Key ID: EFA9B3EC5FD90F8B
39 changed files with 193 additions and 226 deletions

View File

@ -61,15 +61,15 @@ public interface PlayerSaveResult {
}
/**
* Gets the old username involved in the result.
* Gets the previous username involved in the result.
*
* <p>Returns null when the result doesn't {@link #includes(Outcome) include} the
* {@link Outcome#USERNAME_UPDATED} status.</p>
*
* @return the old username
* @return the previous username
* @see Outcome#USERNAME_UPDATED
*/
@Nullable String getOldUsername();
@Nullable String getPreviousUsername();
/**
* Gets the other uuids involved in the result.

View File

@ -26,6 +26,8 @@
package net.luckperms.api.node;
import net.luckperms.api.node.types.ChatMetaNode;
import net.luckperms.api.node.types.PrefixNode;
import net.luckperms.api.node.types.SuffixNode;
import org.checkerframework.checker.nullness.qual.NonNull;
@ -37,12 +39,32 @@ public enum ChatMetaType {
/**
* Represents a prefix
*/
PREFIX(NodeType.PREFIX),
PREFIX(NodeType.PREFIX) {
@Override
public ChatMetaNode.@NonNull Builder<?, ?> builder() {
return PrefixNode.builder();
}
@Override
public ChatMetaNode.@NonNull Builder<?, ?> builder(@NonNull String prefix, int priority) {
return PrefixNode.builder(prefix, priority);
}
},
/**
* Represents a suffix
*/
SUFFIX(NodeType.SUFFIX);
SUFFIX(NodeType.SUFFIX) {
@Override
public ChatMetaNode.@NonNull Builder<?, ?> builder() {
return SuffixNode.builder();
}
@Override
public ChatMetaNode.@NonNull Builder<?, ?> builder(@NonNull String suffix, int priority) {
return SuffixNode.builder(suffix, priority);
}
};
private final String name;
private final NodeType<? extends ChatMetaNode<?, ?>> nodeType;
@ -61,6 +83,22 @@ public enum ChatMetaType {
return this.nodeType;
}
/**
* Creates a {@link ChatMetaNode.Builder} for the {@link ChatMetaType}.
*
* @return a builder
*/
public abstract ChatMetaNode.@NonNull Builder<?, ?> builder();
/**
* Creates a {@link ChatMetaNode.Builder} for the {@link ChatMetaType}.
*
* @param value the value to set
* @param priority the priority to set
* @return a builder
*/
public abstract ChatMetaNode.@NonNull Builder<?, ?> builder(@NonNull String value, int priority);
@Override
public String toString() {
return this.name;

View File

@ -26,7 +26,6 @@
package net.luckperms.api.node;
import net.luckperms.api.LuckPermsProvider;
import net.luckperms.api.context.ContextSet;
import net.luckperms.api.context.ImmutableContextSet;
import net.luckperms.api.node.metadata.NodeMetadataKey;
import net.luckperms.api.node.types.DisplayNameNode;
@ -42,7 +41,7 @@ import org.checkerframework.checker.nullness.qual.NonNull;
import org.checkerframework.checker.nullness.qual.Nullable;
import java.time.Instant;
import java.util.List;
import java.util.Collection;
import java.util.Optional;
import java.util.stream.Stream;
@ -134,21 +133,6 @@ public interface Node {
return !getValue();
}
/**
* Gets if this node applies globally, and therefore has no specific context.
*
* @return true if this node applies globally, and has no specific context
*/
boolean appliesGlobally();
/**
* Gets if this node should apply in the given context
*
* @param contextSet the context set
* @return true if the node should apply
*/
boolean shouldApplyWithContext(@NonNull ContextSet contextSet);
/**
* Resolves any shorthand parts of this node and returns the full list of
* resolved nodes.
@ -157,7 +141,7 @@ public interface Node {
*
* @return a list of full nodes
*/
@NonNull List<String> resolveShorthand();
@NonNull Collection<String> resolveShorthand();
/**
* Gets if this node is assigned temporarily.
@ -172,7 +156,7 @@ public interface Node {
* @return the {@link Instant} when this node will expire, or null if it
* doesn't have an expiry time
*/
@Nullable Instant getExpiry() throws IllegalStateException;
@Nullable Instant getExpiry();
/**
* Gets if the node has expired.

View File

@ -173,7 +173,7 @@ public class MigrationBPermissions extends SubCommand<Object> {
migrateHolder(world, user, lpUser);
plugin.getStorage().saveUser(lpUser);
plugin.getUserManager().cleanup(lpUser);
plugin.getUserManager().getHouseKeeper().cleanup(lpUser.getUniqueId());
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});
@ -220,12 +220,12 @@ public class MigrationBPermissions extends SubCommand<Object> {
}
if (meta.getKey().equalsIgnoreCase("prefix")) {
holder.setNode(DataType.NORMAL, Prefix.builder(c.getPriority(), meta.getValue()).withContext(DefaultContextKeys.WORLD_KEY, world.getName()).build(), true);
holder.setNode(DataType.NORMAL, Prefix.builder(meta.getValue(), c.getPriority()).withContext(DefaultContextKeys.WORLD_KEY, world.getName()).build(), true);
continue;
}
if (meta.getKey().equalsIgnoreCase("suffix")) {
holder.setNode(DataType.NORMAL, Suffix.builder(c.getPriority(), meta.getValue()).withContext(DefaultContextKeys.WORLD_KEY, world.getName()).build(), true);
holder.setNode(DataType.NORMAL, Suffix.builder(meta.getValue(), c.getPriority()).withContext(DefaultContextKeys.WORLD_KEY, world.getName()).build(), true);
continue;
}

View File

@ -156,9 +156,9 @@ public class MigrationGroupManager extends SubCommand<Object> {
if (key.equals("build")) continue;
if (key.equals("prefix")) {
groups.get(groupName).add(Prefix.builder(50, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
groups.get(groupName).add(Prefix.builder(value, 50).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
} else if (key.equals("suffix")) {
groups.get(groupName).add(Suffix.builder(50, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
groups.get(groupName).add(Suffix.builder(value, 50).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
} else {
groups.get(groupName).add(Meta.builder(key, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
}
@ -209,9 +209,9 @@ public class MigrationGroupManager extends SubCommand<Object> {
if (key.equals("build")) continue;
if (key.equals("prefix")) {
users.get(id).add(Prefix.builder(100, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
users.get(id).add(Prefix.builder(value, 100).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
} else if (key.equals("suffix")) {
users.get(id).add(Suffix.builder(100, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
users.get(id).add(Suffix.builder(value, 100).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
} else {
users.get(id).add(Meta.builder(key, value).withContext(DefaultContextKeys.WORLD_KEY, worldMappingFunc.apply(world)).build());
}
@ -256,7 +256,7 @@ public class MigrationGroupManager extends SubCommand<Object> {
}
plugin.getStorage().saveUser(user);
plugin.getUserManager().cleanup(user);
plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});

View File

@ -116,7 +116,7 @@ public class MigrationPermissionsBukkit extends SubCommand<Object> {
migrate(lpUser, usersSection.getConfigurationSection(key));
}
plugin.getUserManager().cleanup(lpUser);
plugin.getUserManager().getHouseKeeper().cleanup(lpUser.getUniqueId());
plugin.getStorage().saveUser(lpUser);
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});

View File

@ -180,7 +180,7 @@ public class MigrationPermissionsEx extends SubCommand<Object> {
// migrate data
migrateEntity(user, lpUser, userWeight);
plugin.getUserManager().cleanup(lpUser);
plugin.getUserManager().getHouseKeeper().cleanup(lpUser.getUniqueId());
plugin.getStorage().saveUser(lpUser);
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});
@ -278,11 +278,11 @@ public class MigrationPermissionsEx extends SubCommand<Object> {
String suffix = entity.getOwnSuffix();
if (prefix != null && !prefix.isEmpty()) {
holder.setNode(DataType.NORMAL, Prefix.builder(weight, prefix).build(), true);
holder.setNode(DataType.NORMAL, Prefix.builder(prefix, weight).build(), true);
}
if (suffix != null && !suffix.isEmpty()) {
holder.setNode(DataType.NORMAL, Suffix.builder(weight, suffix).build(), true);
holder.setNode(DataType.NORMAL, Suffix.builder(suffix, weight).build(), true);
}
// migrate options

View File

@ -190,9 +190,9 @@ public class MigrationPowerfulPerms extends SubCommand<Object> {
}
if (server != null) {
group.setNode(DataType.NORMAL, Prefix.builder(g.getRank(), prefix.getValue()).withContext(DefaultContextKeys.SERVER_KEY, server).build(), true);
group.setNode(DataType.NORMAL, Prefix.builder(prefix.getValue(), g.getRank()).withContext(DefaultContextKeys.SERVER_KEY, server).build(), true);
} else {
group.setNode(DataType.NORMAL, Prefix.builder(g.getRank(), prefix.getValue()).build(), true);
group.setNode(DataType.NORMAL, Prefix.builder(prefix.getValue(), g.getRank()).build(), true);
}
}
@ -205,9 +205,9 @@ public class MigrationPowerfulPerms extends SubCommand<Object> {
}
if (server != null) {
group.setNode(DataType.NORMAL, Suffix.builder(g.getRank(), suffix.getValue()).withContext(DefaultContextKeys.SERVER_KEY, server).build(), true);
group.setNode(DataType.NORMAL, Suffix.builder(suffix.getValue(), g.getRank()).withContext(DefaultContextKeys.SERVER_KEY, server).build(), true);
} else {
group.setNode(DataType.NORMAL, Suffix.builder(g.getRank(), suffix.getValue()).build(), true);
group.setNode(DataType.NORMAL, Suffix.builder(suffix.getValue(), g.getRank()).build(), true);
}
}
@ -252,11 +252,11 @@ public class MigrationPowerfulPerms extends SubCommand<Object> {
String suffix = joinFuture(pm.getPlayerOwnSuffix(uuid));
if (prefix != null && !prefix.isEmpty()) {
user.setNode(DataType.NORMAL, Prefix.builder(maxWeight.get(), prefix).build(), true);
user.setNode(DataType.NORMAL, Prefix.builder(prefix, maxWeight.get()).build(), true);
}
if (suffix != null && !suffix.isEmpty()) {
user.setNode(DataType.NORMAL, Suffix.builder(maxWeight.get(), suffix).build(), true);
user.setNode(DataType.NORMAL, Suffix.builder(suffix, maxWeight.get()).build(), true);
}
Group primaryGroup = joinFuture(pm.getPlayerPrimaryGroup(uuid));
@ -268,7 +268,7 @@ public class MigrationPowerfulPerms extends SubCommand<Object> {
}
}
plugin.getUserManager().cleanup(user);
plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
plugin.getStorage().saveUser(user);
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});

View File

@ -186,7 +186,7 @@ public class MigrationZPermissions extends SubCommand<Object> {
user.getPrimaryGroup().setStoredValue(MigrationUtils.standardizeName(service.getPlayerPrimaryGroup(u)));
plugin.getUserManager().cleanup(user);
plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
plugin.getStorage().saveUser(user);
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});
@ -226,9 +226,9 @@ public class MigrationZPermissions extends SubCommand<Object> {
if (valueString.isEmpty()) continue;
if (key.equals("prefix")) {
holder.setNode(DataType.NORMAL, Prefix.builder(weight, valueString).build(), true);
holder.setNode(DataType.NORMAL, Prefix.builder(valueString, weight).build(), true);
} else if (key.equals("suffix")) {
holder.setNode(DataType.NORMAL, Suffix.builder(weight, valueString).build(), true);
holder.setNode(DataType.NORMAL, Suffix.builder(valueString, weight).build(), true);
} else {
holder.setNode(DataType.NORMAL, Meta.builder(key, valueString).build(), true);
}

View File

@ -278,7 +278,7 @@ public class LuckPermsVaultChat extends AbstractVaultChat {
metaAccumulator.complete();
int priority = metaAccumulator.getChatMeta(type).keySet().stream().mapToInt(e -> e).max().orElse(0) + 10;
NodeBuilder chatMetaNode = type == ChatMetaType.PREFIX ? Prefix.builder(priority, value) : Suffix.builder(priority, value);
NodeBuilder chatMetaNode = type == ChatMetaType.PREFIX ? Prefix.builder(value, priority) : Suffix.builder(value, priority);
chatMetaNode.withContext(DefaultContextKeys.SERVER_KEY, this.vaultPermission.getVaultServer());
chatMetaNode.withContext(DefaultContextKeys.WORLD_KEY, world);
@ -301,9 +301,9 @@ public class LuckPermsVaultChat extends AbstractVaultChat {
NodeBuilder metaNode;
if (key.equalsIgnoreCase("prefix")) {
metaNode = Prefix.builder(100, value.toString());
metaNode = Prefix.builder(value.toString(), 100);
} else if (key.equalsIgnoreCase("suffix")) {
metaNode = Suffix.builder(100, value.toString());
metaNode = Suffix.builder(value.toString(), 100);
} else {
metaNode = Meta.builder(key, value.toString());
}

View File

@ -264,7 +264,7 @@ public class LuckPermsVaultPermission extends AbstractVaultPermission {
ContextSet contexts = getQueryOptions(uuid, world).context();
String[] ret = user.normalData().immutableInheritance().values().stream()
.filter(n -> n.shouldApplyWithContext(contexts))
.filter(n -> n.getContexts().isSatisfiedBy(contexts))
.map(n -> {
Group group = this.plugin.getGroupManager().getIfLoaded(n.getGroupName());
if (group != null) {

View File

@ -121,7 +121,7 @@ public class MigrationBungeePerms extends SubCommand<Object> {
migrateHolder(u, u.getGroupsString(), userWeight, user);
plugin.getStorage().saveUser(user);
plugin.getUserManager().cleanup(user);
plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
log.logProgress("Migrated {} users so far.", userCount.incrementAndGet(), ProgressLogger.DEFAULT_NOTIFY_FREQUENCY);
});
@ -165,10 +165,10 @@ public class MigrationBungeePerms extends SubCommand<Object> {
String suffix = entity.getSuffix();
if (prefix != null && !prefix.isEmpty()) {
holder.setNode(DataType.NORMAL, Prefix.builder(weight, prefix).build(), true);
holder.setNode(DataType.NORMAL, Prefix.builder(prefix, weight).build(), true);
}
if (suffix != null && !suffix.isEmpty()) {
holder.setNode(DataType.NORMAL, Suffix.builder(weight, suffix).build(), true);
holder.setNode(DataType.NORMAL, Suffix.builder(suffix, weight).build(), true);
}
}
}

View File

@ -93,12 +93,12 @@ public class ApiPermissionHolder implements net.luckperms.api.model.PermissionHo
}
@Override
public @NonNull net.luckperms.api.model.PermissionHolder.NodeMap data() {
public @NonNull NodeMap data() {
return this.normalData;
}
@Override
public @NonNull net.luckperms.api.model.PermissionHolder.NodeMap transientData() {
public @NonNull NodeMap transientData() {
return this.transientData;
}

View File

@ -183,7 +183,7 @@ public class Exporter implements Runnable {
})
.add("nodes", NodeJsonSerializer.serializeNodes(user.normalData().asSet()))
.toJson());
this.plugin.getUserManager().cleanup(user);
this.plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
userCount.incrementAndGet();
}, executor));
}

View File

@ -109,7 +109,7 @@ public class Importer implements Runnable {
}
user.setNodes(DataType.NORMAL, userData.nodes);
this.plugin.getStorage().saveUser(user).join();
this.plugin.getUserManager().cleanup(user);
this.plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
}
@Override

View File

@ -29,11 +29,9 @@ import com.google.common.collect.ImmutableList;
import com.google.common.collect.Maps;
import me.lucko.luckperms.common.calculator.result.TristateResult;
import me.lucko.luckperms.common.node.factory.NodeBuilders;
import me.lucko.luckperms.common.node.types.RegexPermission;
import net.luckperms.api.node.Node;
import net.luckperms.api.node.Tristate;
import net.luckperms.api.node.types.RegexPermissionNode;
import java.util.Collections;
import java.util.List;
@ -59,12 +57,12 @@ public class RegexProcessor extends AbstractPermissionProcessor implements Permi
public void refresh() {
ImmutableList.Builder<Map.Entry<Pattern, TristateResult>> builder = ImmutableList.builder();
for (Map.Entry<String, Boolean> e : this.sourceMap.entrySet()) {
Node builtNode = NodeBuilders.determineMostApplicable(e.getKey()).build();
if (!(builtNode instanceof RegexPermissionNode)) {
RegexPermission.Builder regexPerm = RegexPermission.parse(e.getKey());
if (regexPerm == null) {
continue;
}
Pattern pattern = ((RegexPermissionNode) builtNode).getPattern().orElse(null);
Pattern pattern = regexPerm.build().getPattern().orElse(null);
if (pattern == null) {
continue;
}

View File

@ -40,8 +40,6 @@ import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
@ -87,7 +85,7 @@ public class MetaAddChatMeta extends SharedSubCommand {
return CommandResult.NO_PERMISSION;
}
DataMutateResult result = holder.setNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).withContext(context).build(), true);
DataMutateResult result = holder.setNode(DataType.NORMAL, this.type.builder(meta, priority).withContext(context).build(), true);
if (result.wasSuccessful()) {
TextComponent.Builder builder = Message.ADD_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();
HoverEvent event = HoverEvent.showText(TextUtils.fromLegacy(

View File

@ -41,8 +41,6 @@ import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.DurationFormatter;
@ -56,7 +54,6 @@ import net.luckperms.api.model.DataType;
import net.luckperms.api.model.TemporaryDataMutateResult;
import net.luckperms.api.model.TemporaryMergeBehaviour;
import net.luckperms.api.node.ChatMetaType;
import net.luckperms.api.util.Result;
import java.util.List;
@ -93,9 +90,9 @@ public class MetaAddTempChatMeta extends SharedSubCommand {
return CommandResult.NO_PERMISSION;
}
TemporaryDataMutateResult ret = holder.setNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).expiry(duration).withContext(context).build(), modifier);
TemporaryDataMutateResult ret = holder.setNode(DataType.NORMAL, this.type.builder(meta, priority).expiry(duration).withContext(context).build(), modifier);
if (((Result) ret.getResult()).wasSuccessful()) {
if (ret.getResult().wasSuccessful()) {
duration = ret.getMergedNode().getExpiry().getEpochSecond();
TextComponent.Builder builder = Message.ADD_TEMP_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, DurationFormatter.LONG.formatDateDiff(duration), MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();

View File

@ -40,8 +40,6 @@ import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
@ -100,7 +98,7 @@ public class MetaRemoveChatMeta extends SharedSubCommand {
return CommandResult.SUCCESS;
}
DataMutateResult result = holder.unsetNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).withContext(context).build());
DataMutateResult result = holder.unsetNode(DataType.NORMAL, this.type.builder(meta, priority).withContext(context).build());
if (result.wasSuccessful()) {
TextComponent.Builder builder = Message.REMOVE_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();

View File

@ -40,8 +40,6 @@ import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
@ -100,7 +98,7 @@ public class MetaRemoveTempChatMeta extends SharedSubCommand {
return CommandResult.SUCCESS;
}
DataMutateResult result = holder.unsetNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).expiry(10L).withContext(context).build());
DataMutateResult result = holder.unsetNode(DataType.NORMAL, this.type.builder(meta, priority).expiry(10L).withContext(context).build());
if (result.wasSuccessful()) {
TextComponent.Builder builder = Message.REMOVE_TEMP_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();

View File

@ -42,8 +42,6 @@ import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.Group;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
@ -123,7 +121,7 @@ public class MetaSetChatMeta extends SharedSubCommand {
}
}
DataMutateResult result = holder.setNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).withContext(context).build(), true);
DataMutateResult result = holder.setNode(DataType.NORMAL, this.type.builder(meta, priority).withContext(context).build(), true);
if (result.wasSuccessful()) {
TextComponent.Builder builder = Message.ADD_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();
HoverEvent event = HoverEvent.showText(TextUtils.fromLegacy(

View File

@ -43,8 +43,6 @@ import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.Group;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.node.types.Prefix;
import me.lucko.luckperms.common.node.types.Suffix;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.DurationFormatter;
@ -59,7 +57,6 @@ import net.luckperms.api.model.TemporaryDataMutateResult;
import net.luckperms.api.model.TemporaryMergeBehaviour;
import net.luckperms.api.node.ChatMetaType;
import net.luckperms.api.query.QueryOptions;
import net.luckperms.api.util.Result;
import java.util.List;
import java.util.OptionalInt;
@ -133,9 +130,9 @@ public class MetaSetTempChatMeta extends SharedSubCommand {
}
}
TemporaryDataMutateResult ret = holder.setNode(DataType.NORMAL, ((this.type == ChatMetaType.PREFIX ? Prefix.builder(priority, meta) : Suffix.builder(priority, meta))).expiry(duration).withContext(context).build(), modifier);
TemporaryDataMutateResult ret = holder.setNode(DataType.NORMAL, this.type.builder(meta, priority).expiry(duration).withContext(context).build(), modifier);
if (((Result) ret.getResult()).wasSuccessful()) {
if (ret.getResult().wasSuccessful()) {
duration = ret.getMergedNode().getExpiry().getEpochSecond();
TextComponent.Builder builder = Message.ADD_TEMP_CHATMETA_SUCCESS.asComponent(plugin.getLocaleManager(), holder.getFormattedDisplayName(), this.type.name().toLowerCase(), meta, priority, DurationFormatter.LONG.formatDateDiff(duration), MessageUtils.contextSetToString(plugin.getLocaleManager(), context)).toBuilder();

View File

@ -31,7 +31,6 @@ import me.lucko.luckperms.common.command.CommandResult;
import me.lucko.luckperms.common.command.abstraction.SubCommand;
import me.lucko.luckperms.common.command.access.ArgumentPermissions;
import me.lucko.luckperms.common.command.access.CommandPermission;
import me.lucko.luckperms.common.config.ConfigKeys;
import me.lucko.luckperms.common.context.contextset.ImmutableContextSetImpl;
import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
@ -40,24 +39,10 @@ import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
import me.lucko.luckperms.common.util.gson.GsonProvider;
import me.lucko.luckperms.common.web.AbstractHttpClient;
import me.lucko.luckperms.common.web.WebEditor;
import net.kyori.text.Component;
import net.kyori.text.TextComponent;
import net.kyori.text.event.ClickEvent;
import net.kyori.text.event.HoverEvent;
import net.kyori.text.format.TextColor;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.nio.charset.StandardCharsets;
import java.util.Collections;
import java.util.List;
import java.util.zip.GZIPOutputStream;
public class HolderEditor<T extends PermissionHolder> extends SubCommand<T> {
public HolderEditor(LocaleManager locale, boolean user) {
@ -73,37 +58,8 @@ public class HolderEditor<T extends PermissionHolder> extends SubCommand<T> {
Message.EDITOR_START.send(sender);
// form the payload data
JsonObject payload = WebEditor.formPayload(Collections.singletonList(holder), Collections.emptyList(), sender, label, plugin);
// upload the payload data to gist
ByteArrayOutputStream bytesOut = new ByteArrayOutputStream();
try (Writer writer = new OutputStreamWriter(new GZIPOutputStream(bytesOut), StandardCharsets.UTF_8)) {
GsonProvider.prettyPrinting().toJson(payload, writer);
} catch (IOException e) {
e.printStackTrace();
}
String pasteId;
try {
pasteId = plugin.getBytebin().postContent(bytesOut.toByteArray(), AbstractHttpClient.JSON_TYPE, false).key();
} catch (IOException e) {
Message.EDITOR_UPLOAD_FAILURE.send(sender);
return CommandResult.STATE_ERROR;
}
// form a url for the editor
String url = plugin.getConfiguration().get(ConfigKeys.WEB_EDITOR_URL_PATTERN) + "#" + pasteId;
Message.EDITOR_URL.send(sender);
Component message = TextComponent.builder(url).color(TextColor.AQUA)
.clickEvent(ClickEvent.openUrl(url))
.hoverEvent(HoverEvent.showText(TextComponent.of("Click to open the editor.").color(TextColor.GRAY)))
.build();
sender.sendMessage(message);
return CommandResult.SUCCESS;
return WebEditor.post(payload, sender, plugin);
}
}

View File

@ -32,35 +32,26 @@ import me.lucko.luckperms.common.command.abstraction.SingleCommand;
import me.lucko.luckperms.common.command.access.ArgumentPermissions;
import me.lucko.luckperms.common.command.access.CommandPermission;
import me.lucko.luckperms.common.command.utils.ArgumentParser;
import me.lucko.luckperms.common.config.ConfigKeys;
import me.lucko.luckperms.common.locale.LocaleManager;
import me.lucko.luckperms.common.locale.command.CommandSpec;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.model.Track;
import me.lucko.luckperms.common.model.User;
import me.lucko.luckperms.common.plugin.LuckPermsPlugin;
import me.lucko.luckperms.common.sender.Sender;
import me.lucko.luckperms.common.util.Predicates;
import me.lucko.luckperms.common.util.gson.GsonProvider;
import me.lucko.luckperms.common.web.AbstractHttpClient;
import me.lucko.luckperms.common.web.WebEditor;
import net.kyori.text.Component;
import net.kyori.text.TextComponent;
import net.kyori.text.event.ClickEvent;
import net.kyori.text.event.HoverEvent;
import net.kyori.text.format.TextColor;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.zip.GZIPOutputStream;
import java.util.Set;
import java.util.UUID;
public class EditorCommand extends SingleCommand {
private static final int MAX_USERS = 500;
public EditorCommand(LocaleManager locale) {
super(CommandSpec.EDITOR.localize(locale), "Editor", CommandPermission.EDITOR, Predicates.notInRange(0, 1));
}
@ -83,6 +74,9 @@ public class EditorCommand extends SingleCommand {
List<PermissionHolder> holders = new ArrayList<>();
List<Track> tracks = new ArrayList<>();
if (type.includingGroups) {
// run a sync task
plugin.getSyncTaskBuffer().requestDirectly();
plugin.getGroupManager().getAll().values().stream()
.sorted((o1, o2) -> {
int i = Integer.compare(o2.getWeight().orElse(0), o1.getWeight().orElse(0));
@ -92,9 +86,29 @@ public class EditorCommand extends SingleCommand {
tracks = new ArrayList<>(plugin.getTrackManager().getAll().values());
}
if (type.includingUsers) {
Set<UUID> users = new LinkedHashSet<>();
// online players first
plugin.getUserManager().getAll().values().stream()
.sorted((o1, o2) -> o1.getFormattedDisplayName().compareToIgnoreCase(o2.getFormattedDisplayName()))
.forEach(holders::add);
.map(User::getUniqueId)
.forEach(users::add);
// then fill up with other users
users.addAll(plugin.getStorage().getUniqueUsers().join());
users.stream().limit(MAX_USERS).forEach(uuid -> {
User user = plugin.getUserManager().getIfLoaded(uuid);
if (user != null) {
holders.add(user);
} else {
user = plugin.getStorage().loadUser(uuid, null).join();
if (user != null) {
holders.add(user);
}
plugin.getUserManager().getHouseKeeper().cleanup(uuid);
}
});
}
if (holders.isEmpty()) {
@ -114,37 +128,8 @@ public class EditorCommand extends SingleCommand {
Message.EDITOR_START.send(sender);
// form the payload data
JsonObject payload = WebEditor.formPayload(holders, tracks, sender, label, plugin);
// upload the payload data to gist
ByteArrayOutputStream bytesOut = new ByteArrayOutputStream();
try (Writer writer = new OutputStreamWriter(new GZIPOutputStream(bytesOut), StandardCharsets.UTF_8)) {
GsonProvider.prettyPrinting().toJson(payload, writer);
} catch (IOException e) {
e.printStackTrace();
}
String pasteId;
try {
pasteId = plugin.getBytebin().postContent(bytesOut.toByteArray(), AbstractHttpClient.JSON_TYPE, false).key();
} catch (IOException e) {
Message.EDITOR_UPLOAD_FAILURE.send(sender);
return CommandResult.STATE_ERROR;
}
// form a url for the editor
String url = plugin.getConfiguration().get(ConfigKeys.WEB_EDITOR_URL_PATTERN) + "#" + pasteId;
Message.EDITOR_URL.send(sender);
Component message = TextComponent.builder(url).color(TextColor.AQUA)
.clickEvent(ClickEvent.openUrl(url))
.hoverEvent(HoverEvent.showText(TextComponent.of("Click to open the editor.").color(TextColor.GRAY)))
.build();
sender.sendMessage(message);
return CommandResult.SUCCESS;
return WebEditor.post(payload, sender, plugin);
}
private enum Type {

View File

@ -92,7 +92,7 @@ public class TreeCommand extends SingleCommand {
Message.TREE_UPLOAD_START.send(sender);
PermissionCache permissionData = user == null ? null : user.getCachedData().getPermissionData(plugin.getQueryOptionsForUser(user).orElse(plugin.getContextManager().getStaticQueryOptions()));
String id = view.uploadPasteData(plugin.getBytebin(), sender, user, permissionData);
String url = plugin.getConfiguration().get(ConfigKeys.TREE_VIEWER_URL_PATTERN) + "#" + id;
String url = plugin.getConfiguration().get(ConfigKeys.TREE_VIEWER_URL_PATTERN) + id;
Message.TREE_URL.send(sender);

View File

@ -113,7 +113,7 @@ public class VerboseCommand extends SingleCommand {
} else {
Message.VERBOSE_UPLOAD_START.send(sender);
String id = listener.uploadPasteData(plugin.getBytebin());
String url = plugin.getConfiguration().get(ConfigKeys.VERBOSE_VIEWER_URL_PATTERN) + "#" + id;
String url = plugin.getConfiguration().get(ConfigKeys.VERBOSE_VIEWER_URL_PATTERN) + id;
Message.VERBOSE_RESULTS_URL.send(sender);

View File

@ -82,7 +82,7 @@ public class UserClone extends SubCommand<User> {
.build().submit(plugin, sender);
StorageAssistant.save(otherUser, sender, plugin);
plugin.getUserManager().cleanup(otherUser);
plugin.getUserManager().getHouseKeeper().cleanup(otherUser.getUniqueId());
return CommandResult.SUCCESS;
}
}

View File

@ -138,7 +138,7 @@ public class UserMainCommand extends MainCommand<User, UserIdentifier> {
@Override
protected void cleanup(User user, LuckPermsPlugin plugin) {
plugin.getUserManager().cleanup(user);
plugin.getUserManager().getHouseKeeper().cleanup(user.getUniqueId());
}
@Override

View File

@ -528,17 +528,17 @@ public final class ConfigKeys {
/**
* The URL of the web editor
*/
public static final ConfigKey<String> WEB_EDITOR_URL_PATTERN = stringKey("web-editor-url", "https://luckperms.github.io/editor/");
public static final ConfigKey<String> WEB_EDITOR_URL_PATTERN = stringKey("web-editor-url", "https://editor.luckperms.net/");
/**
* The URL of the verbose viewer
*/
public static final ConfigKey<String> VERBOSE_VIEWER_URL_PATTERN = stringKey("verbose-viewer-url", "https://luckperms.github.io/verbose/");
public static final ConfigKey<String> VERBOSE_VIEWER_URL_PATTERN = stringKey("verbose-viewer-url", "https://luckperms.net/verbose/#");
/**
* The URL of the tree viewer
*/
public static final ConfigKey<String> TREE_VIEWER_URL_PATTERN = stringKey("tree-viewer-url", "https://luckperms.github.io/treeview/");
public static final ConfigKey<String> TREE_VIEWER_URL_PATTERN = stringKey("tree-viewer-url", "https://luckperms.net/treeview/#");
private static final Map<String, ConfigKey<?>> KEYS;
private static final int SIZE;

View File

@ -319,7 +319,7 @@ public abstract class PermissionHolder {
if (resolveShorthand) {
for (Node node : entries) {
List<String> shorthand = node.resolveShorthand();
Collection<String> shorthand = node.resolveShorthand();
for (String s : shorthand) {
if (convertToLowercase) {
perms.putIfAbsent(s.toLowerCase(), node.getValue());

View File

@ -129,11 +129,6 @@ public abstract class AbstractUserManager<T extends User> extends AbstractManage
return this.housekeeper;
}
@Override
public void cleanup(User user) {
this.housekeeper.cleanup(user.getUniqueId());
}
@Override
public CompletableFuture<Void> updateAllUsers() {
return CompletableFuture.runAsync(

View File

@ -74,13 +74,6 @@ public interface UserManager<T extends User> extends Manager<UUID, User, T> {
*/
UserHousekeeper getHouseKeeper();
/**
* Unloads the user if a corresponding player is not online
*
* @param user the user
*/
void cleanup(User user);
/**
* Reloads the data of all *online* users
*/

View File

@ -29,19 +29,19 @@ import com.google.common.collect.ImmutableList;
import me.lucko.luckperms.common.node.utils.ShorthandParser;
import net.luckperms.api.context.ContextSet;
import net.luckperms.api.context.ImmutableContextSet;
import net.luckperms.api.node.Node;
import net.luckperms.api.node.NodeBuilder;
import net.luckperms.api.node.NodeEqualityPredicate;
import net.luckperms.api.node.ScopedNode;
import net.luckperms.api.node.metadata.NodeMetadataKey;
import net.luckperms.api.node.types.RegexPermissionNode;
import net.luckperms.api.node.types.PermissionNode;
import org.checkerframework.checker.nullness.qual.NonNull;
import org.checkerframework.checker.nullness.qual.Nullable;
import java.time.Instant;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Optional;
@ -74,7 +74,7 @@ public abstract class AbstractNode<N extends ScopedNode<N, B>, B extends NodeBui
this.contexts = contexts;
this.metadata = metadata;
this.resolvedShorthand = this instanceof RegexPermissionNode ? ImmutableList.of() : ImmutableList.copyOf(ShorthandParser.parseShorthand(this.key));
this.resolvedShorthand = this instanceof PermissionNode ? ImmutableList.copyOf(ShorthandParser.parseShorthand(this.key)) : ImmutableList.of();
this.hashCode = calculateHashCode();
}
@ -101,16 +101,6 @@ public abstract class AbstractNode<N extends ScopedNode<N, B>, B extends NodeBui
return Optional.ofNullable(value);
}
@Override
public boolean appliesGlobally() {
return this.contexts.isEmpty();
}
@Override
public boolean shouldApplyWithContext(@NonNull ContextSet contextSet) {
return this.contexts.isSatisfiedBy(contextSet);
}
@Override
public boolean hasExpiry() {
return this.expireAt != 0L;
@ -127,7 +117,7 @@ public abstract class AbstractNode<N extends ScopedNode<N, B>, B extends NodeBui
}
@Override
public @NonNull List<String> resolveShorthand() {
public @NonNull Collection<String> resolveShorthand() {
return this.resolvedShorthand;
}

View File

@ -53,7 +53,7 @@ public class Prefix extends AbstractNode<PrefixNode, PrefixNode.Builder> impleme
return new Builder();
}
public static Builder builder(int priority, String prefix) {
public static Builder builder(String prefix, int priority) {
return builder().prefix(prefix).priority(priority);
}

View File

@ -53,7 +53,7 @@ public class Suffix extends AbstractNode<SuffixNode, SuffixNode.Builder> impleme
return new Builder();
}
public static Builder builder(int priority, String suffix) {
public static Builder builder(String suffix, int priority) {
return builder().suffix(suffix).priority(priority);
}

View File

@ -590,7 +590,7 @@ public abstract class AbstractConfigurateStorage implements StorageImplementatio
if (entry == null) {
continue;
}
nodes.add(readMetaAttributes(entry.getValue(), c -> Prefix.builder(c.getNode("priority").getInt(0), entry.getKey())));
nodes.add(readMetaAttributes(entry.getValue(), c -> Prefix.builder(entry.getKey(), c.getNode("priority").getInt(0))));
}
}
@ -601,7 +601,7 @@ public abstract class AbstractConfigurateStorage implements StorageImplementatio
if (entry == null) {
continue;
}
nodes.add(readMetaAttributes(entry.getValue(), c -> Suffix.builder(c.getNode("priority").getInt(0), entry.getKey())));
nodes.add(readMetaAttributes(entry.getValue(), c -> Suffix.builder(entry.getKey(), c.getNode("priority").getInt(0))));
}
}

View File

@ -69,12 +69,12 @@ public final class PlayerSaveResultImpl implements PlayerSaveResult {
}
private final Set<Outcome> outcomes;
private final @Nullable String oldUsername;
private final @Nullable String previousUsername;
private final @Nullable Set<UUID> otherUuids;
private PlayerSaveResultImpl(EnumSet<Outcome> outcomes, @Nullable String oldUsername, @Nullable Set<UUID> otherUuids) {
private PlayerSaveResultImpl(EnumSet<Outcome> outcomes, @Nullable String previousUsername, @Nullable Set<UUID> otherUuids) {
this.outcomes = ImmutableSet.copyOf(outcomes);
this.oldUsername = oldUsername;
this.previousUsername = previousUsername;
this.otherUuids = otherUuids;
}
@ -92,7 +92,7 @@ public final class PlayerSaveResultImpl implements PlayerSaveResult {
public PlayerSaveResultImpl withOtherUuidsPresent(@NonNull Set<UUID> otherUuids) {
EnumSet<Outcome> outcomes = EnumSet.copyOf(this.outcomes);
outcomes.add(Outcome.OTHER_UNIQUE_IDS_PRESENT_FOR_USERNAME);
return new PlayerSaveResultImpl(outcomes, this.oldUsername, ImmutableSet.copyOf(otherUuids));
return new PlayerSaveResultImpl(outcomes, this.previousUsername, ImmutableSet.copyOf(otherUuids));
}
@Override
@ -101,8 +101,8 @@ public final class PlayerSaveResultImpl implements PlayerSaveResult {
}
@Override
public @Nullable String getOldUsername() {
return this.oldUsername;
public @Nullable String getPreviousUsername() {
return this.previousUsername;
}
@Override
@ -116,17 +116,17 @@ public final class PlayerSaveResultImpl implements PlayerSaveResult {
if (that == null || getClass() != that.getClass()) return false;
PlayerSaveResultImpl result = (PlayerSaveResultImpl) that;
return Objects.equals(this.outcomes, result.outcomes) &&
Objects.equals(this.oldUsername, result.oldUsername) &&
Objects.equals(this.previousUsername, result.previousUsername) &&
Objects.equals(this.otherUuids, result.otherUuids);
}
@Override
public int hashCode() {
return Objects.hash(this.outcomes, this.oldUsername, this.otherUuids);
return Objects.hash(this.outcomes, this.previousUsername, this.otherUuids);
}
@Override
public String toString() {
return "PlayerSaveResult(outcomes=" + this.outcomes + ", oldUsername=" + this.oldUsername + ", otherUuids=" + this.otherUuids + ")";
return "PlayerSaveResult(outcomes=" + this.outcomes + ", previousUsername=" + this.previousUsername + ", otherUuids=" + this.otherUuids + ")";
}
}

View File

@ -28,7 +28,10 @@ package me.lucko.luckperms.common.web;
import com.google.common.base.Preconditions;
import com.google.gson.JsonObject;
import me.lucko.luckperms.common.command.CommandResult;
import me.lucko.luckperms.common.config.ConfigKeys;
import me.lucko.luckperms.common.context.ContextSetJsonSerializer;
import me.lucko.luckperms.common.locale.message.Message;
import me.lucko.luckperms.common.model.PermissionHolder;
import me.lucko.luckperms.common.model.Track;
import me.lucko.luckperms.common.node.utils.NodeJsonSerializer;
@ -38,16 +41,26 @@ import me.lucko.luckperms.common.util.gson.GsonProvider;
import me.lucko.luckperms.common.util.gson.JArray;
import me.lucko.luckperms.common.util.gson.JObject;
import net.kyori.text.Component;
import net.kyori.text.TextComponent;
import net.kyori.text.event.ClickEvent;
import net.kyori.text.event.HoverEvent;
import net.kyori.text.format.TextColor;
import okhttp3.Request;
import okhttp3.Response;
import okhttp3.ResponseBody;
import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.zip.GZIPOutputStream;
/**
* Utility methods for interacting with the LuckPerms web permission editor.
@ -111,6 +124,37 @@ public final class WebEditor {
.toJson();
}
public static CommandResult post(JsonObject payload, Sender sender, LuckPermsPlugin plugin) {
// upload the payload data to gist
ByteArrayOutputStream bytesOut = new ByteArrayOutputStream();
try (Writer writer = new OutputStreamWriter(new GZIPOutputStream(bytesOut), StandardCharsets.UTF_8)) {
GsonProvider.prettyPrinting().toJson(payload, writer);
} catch (IOException e) {
e.printStackTrace();
}
String pasteId;
try {
pasteId = plugin.getBytebin().postContent(bytesOut.toByteArray(), AbstractHttpClient.JSON_TYPE, false).key();
} catch (IOException e) {
Message.EDITOR_UPLOAD_FAILURE.send(sender);
return CommandResult.STATE_ERROR;
}
// form a url for the editor
String url = plugin.getConfiguration().get(ConfigKeys.WEB_EDITOR_URL_PATTERN) + pasteId;
Message.EDITOR_URL.send(sender);
Component message = TextComponent.builder(url).color(TextColor.AQUA)
.clickEvent(ClickEvent.openUrl(url))
.hoverEvent(HoverEvent.showText(TextComponent.of("Click to open the editor.").color(TextColor.GRAY)))
.build();
sender.sendMessage(message);
return CommandResult.SUCCESS;
}
public static JsonObject readDataFromBytebin(BytebinClient bytebin, String id) {
Request request = new Request.Builder()
.header("User-Agent", bytebin.getUserAgent())

View File

@ -50,7 +50,6 @@ import net.luckperms.api.node.ChatMetaType;
import net.luckperms.api.node.Node;
import net.luckperms.api.node.NodeType;
import net.luckperms.api.node.Tristate;
import net.luckperms.api.node.types.ChatMetaNode;
import net.luckperms.api.node.types.InheritanceNode;
import net.luckperms.api.node.types.MetaNode;
import net.luckperms.api.node.types.PrefixNode;
@ -313,8 +312,7 @@ public class PermissionHolderSubjectData implements LPSubjectData {
int priority = metaAccumulator.getChatMeta(type).keySet().stream().mapToInt(e -> e).max().orElse(0);
priority += 10;
ChatMetaNode.Builder<?, ?> builder = type == ChatMetaType.PREFIX ? Prefix.builder(priority, value) : Suffix.builder(priority, value);
node = builder.withContext(contexts).build();
node = type.builder(value, priority).withContext(contexts).build();
} else {
// standard remove
this.holder.removeIf(this.type, contexts, NodeType.META.predicate(n -> n.getMetaKey().equals(key)), false);