Implement Sponge timings

This commit is contained in:
Luck 2016-10-30 19:35:11 +00:00
parent 17b06c39e9
commit 36bc1553c0
No known key found for this signature in database
GPG Key ID: EFA9B3EC5FD90F8B
13 changed files with 818 additions and 603 deletions

View File

@ -53,6 +53,7 @@ import me.lucko.luckperms.common.utils.LocaleManager;
import me.lucko.luckperms.common.utils.LogFactory;
import me.lucko.luckperms.sponge.contexts.WorldCalculator;
import me.lucko.luckperms.sponge.service.LuckPermsService;
import me.lucko.luckperms.sponge.timings.LPTimings;
import me.lucko.luckperms.sponge.utils.VersionData;
import org.slf4j.Logger;
import org.spongepowered.api.Game;
@ -102,6 +103,7 @@ public class LPSpongePlugin implements LuckPermsPlugin {
private Path configDir;
private Scheduler scheduler = Sponge.getScheduler();
private LPTimings timings;
private final Set<UUID> ignoringLogs = ConcurrentHashMap.newKeySet();
private LPConfiguration configuration;
@ -126,6 +128,7 @@ public class LPSpongePlugin implements LuckPermsPlugin {
public void onEnable(GamePreInitializationEvent event) {
log = LogFactory.wrap(logger);
debugHandler = new DebugHandler();
timings = new LPTimings(this);
getLog().info("Loading configuration...");
configuration = new SpongeConfig(this);

View File

@ -22,12 +22,13 @@
package me.lucko.luckperms.sponge;
import co.aikar.timings.Timing;
import com.google.common.base.Splitter;
import me.lucko.luckperms.api.data.Callback;
import me.lucko.luckperms.common.LuckPermsPlugin;
import me.lucko.luckperms.common.commands.CommandManager;
import me.lucko.luckperms.common.commands.Util;
import me.lucko.luckperms.common.constants.Patterns;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.command.CommandCallable;
import org.spongepowered.api.command.CommandException;
import org.spongepowered.api.command.CommandResult;
@ -42,12 +43,16 @@ import java.util.Optional;
@SuppressWarnings("NullableProblems")
class SpongeCommand extends CommandManager implements CommandCallable {
SpongeCommand(LuckPermsPlugin plugin) {
private final LPSpongePlugin plugin;
SpongeCommand(LPSpongePlugin plugin) {
super(plugin);
this.plugin = plugin;
}
@Override
public CommandResult process(CommandSource source, String s) throws CommandException {
try (Timing ignored = plugin.getTimings().time(LPTiming.ON_COMMAND)) {
onCommand(
SpongeSenderFactory.get(getPlugin()).wrap(source),
"perms",
@ -56,15 +61,20 @@ class SpongeCommand extends CommandManager implements CommandCallable {
);
return CommandResult.success();
}
}
@Override
public List<String> getSuggestions(CommandSource source, String s, @Nullable Location<World> location) throws CommandException {
try (Timing ignored = plugin.getTimings().time(LPTiming.COMMAND_TAB_COMPLETE)) {
return onTabComplete(SpongeSenderFactory.get(getPlugin()).wrap(source), Splitter.on(' ').splitToList(s));
}
}
public List<String> getSuggestions(CommandSource source, String s) throws CommandException {
try (Timing ignored = plugin.getTimings().time(LPTiming.COMMAND_TAB_COMPLETE)) {
return onTabComplete(SpongeSenderFactory.get(getPlugin()).wrap(source), Splitter.on(' ').splitToList(s));
}
}
@Override
public boolean testPermission(CommandSource source) {

View File

@ -22,11 +22,13 @@
package me.lucko.luckperms.sponge;
import co.aikar.timings.Timing;
import me.lucko.luckperms.api.caching.UserData;
import me.lucko.luckperms.api.context.MutableContextSet;
import me.lucko.luckperms.common.constants.Message;
import me.lucko.luckperms.common.users.User;
import me.lucko.luckperms.common.utils.AbstractListener;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.entity.living.player.Player;
import org.spongepowered.api.event.Listener;
import org.spongepowered.api.event.Order;
@ -63,6 +65,7 @@ public class SpongeListener extends AbstractListener {
@SuppressWarnings("deprecation")
@Listener(order = Order.EARLY)
public void onClientLogin(ClientConnectionEvent.Login e) {
try (Timing ignored = plugin.getTimings().time(LPTiming.ON_CLIENT_LOGIN)) {
final GameProfile player = e.getProfile();
final User user = plugin.getUserManager().get(plugin.getUuidCache().getUUID(player.getUniqueId()));
@ -95,6 +98,7 @@ public class SpongeListener extends AbstractListener {
});
}
}
}
@Listener(order = Order.EARLY)
public void onClientJoin(ClientConnectionEvent.Join e) {
@ -104,7 +108,9 @@ public class SpongeListener extends AbstractListener {
@Listener(order = Order.LAST)
public void onClientLeave(ClientConnectionEvent.Disconnect e) {
try (Timing ignored = plugin.getTimings().time(LPTiming.ON_CLIENT_LEAVE)) {
onLeave(e.getTargetEntity().getUniqueId());
plugin.getService().getUserSubjects().unload(plugin.getUuidCache().getUUID(e.getTargetEntity().getUniqueId()));
}
}
}

View File

@ -22,6 +22,7 @@
package me.lucko.luckperms.sponge.service;
import co.aikar.timings.Timing;
import com.google.common.collect.ImmutableList;
import lombok.AccessLevel;
import lombok.EqualsAndHashCode;
@ -30,6 +31,7 @@ import me.lucko.luckperms.api.LocalizedNode;
import me.lucko.luckperms.api.Node;
import me.lucko.luckperms.api.context.ContextSet;
import me.lucko.luckperms.common.groups.Group;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.command.CommandSource;
import org.spongepowered.api.service.permission.NodeTree;
import org.spongepowered.api.service.permission.Subject;
@ -81,6 +83,7 @@ public class LuckPermsGroupSubject extends LuckPermsSubject {
@Override
public Tristate getPermissionValue(ContextSet contexts, String permission) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_GET_PERMISSION_VALUE)) {
Map<String, Boolean> permissions = group.getAllNodesFiltered(service.calculateContexts(contexts)).stream()
.map(LocalizedNode::getNode)
.collect(Collectors.toMap(Node::getPermission, Node::getValue));
@ -98,14 +101,18 @@ public class LuckPermsGroupSubject extends LuckPermsSubject {
t = service.getDefaults().getPermissionValue(LuckPermsService.convertContexts(contexts), permission);
return t;
}
}
@Override
public boolean isChildOf(ContextSet contexts, Subject parent) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_IS_CHILD_OF)) {
return parent instanceof LuckPermsGroupSubject && getPermissionValue(contexts, "group." + parent.getIdentifier()).asBoolean();
}
}
@Override
public List<Subject> getParents(ContextSet contexts) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_GET_PARENTS)) {
List<Subject> subjects = group.getAllNodesFiltered(service.calculateContexts(contexts)).stream()
.map(LocalizedNode::getNode)
.filter(Node::isGroupNode)
@ -118,9 +125,11 @@ public class LuckPermsGroupSubject extends LuckPermsSubject {
return ImmutableList.copyOf(subjects);
}
}
@Override
public Optional<String> getOption(ContextSet contexts, String s) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_GET_OPTION)) {
Optional<String> option;
if (s.equalsIgnoreCase("prefix")) {
option = getChatMeta(contexts, true);
@ -143,11 +152,14 @@ public class LuckPermsGroupSubject extends LuckPermsSubject {
return service.getDefaults().getOption(LuckPermsService.convertContexts(contexts), s);
}
}
@Override
public ContextSet getActiveContextSet() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_GET_ACTIVE_CONTEXTS)) {
return service.getPlugin().getContextManager().getApplicableContext(this);
}
}
private Optional<String> getChatMeta(ContextSet contexts, boolean prefix) {
int priority = Integer.MIN_VALUE;

View File

@ -22,6 +22,7 @@
package me.lucko.luckperms.sponge.service;
import co.aikar.timings.Timing;
import com.google.common.cache.CacheBuilder;
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
@ -38,6 +39,7 @@ import me.lucko.luckperms.sponge.service.collections.UserCollection;
import me.lucko.luckperms.sponge.service.persisted.PersistedCollection;
import me.lucko.luckperms.sponge.service.persisted.SubjectStorage;
import me.lucko.luckperms.sponge.service.simple.SimpleCollection;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.plugin.PluginContainer;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.context.ContextCalculator;
@ -101,8 +103,10 @@ public class LuckPermsService implements PermissionService {
@Override
public SubjectCollection getSubjects(String s) {
try (Timing ignored = plugin.getTimings().time(LPTiming.GET_SUBJECTS)) {
return collections.getUnchecked(s.toLowerCase());
}
}
@Override
public Map<String, SubjectCollection> getKnownSubjects() {

View File

@ -22,6 +22,7 @@
package me.lucko.luckperms.sponge.service;
import co.aikar.timings.Timing;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableSet;
@ -34,6 +35,7 @@ import me.lucko.luckperms.common.groups.Group;
import me.lucko.luckperms.common.users.User;
import me.lucko.luckperms.exceptions.ObjectAlreadyHasException;
import me.lucko.luckperms.exceptions.ObjectLacksException;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.permission.Subject;
import org.spongepowered.api.service.permission.SubjectData;
@ -63,6 +65,7 @@ public class LuckPermsSubjectData implements SubjectData {
@Override
public Map<Set<Context>, Map<String, Boolean>> getAllPermissions() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_GET_PERMISSIONS)) {
Map<Set<Context>, Map<String, Boolean>> perms = new HashMap<>();
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
@ -89,25 +92,21 @@ public class LuckPermsSubjectData implements SubjectData {
}
return map.build();
}
@Override
public Map<String, Boolean> getPermissions(Set<Context> contexts) {
ImmutableMap.Builder<String, Boolean> permissions = ImmutableMap.builder();
(enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(n -> n.shouldApplyWithContext(LuckPermsService.convertContexts(contexts), true))
.forEach(n -> permissions.put(n.getKey(), n.getValue()));
return permissions.build();
}
@Override
public boolean setPermission(Set<Context> set, String s, Tristate tristate) {
public Map<String, Boolean> getPermissions(Set<Context> contexts) {
return getAllPermissions().getOrDefault(contexts, ImmutableMap.of());
}
@Override
public boolean setPermission(Set<Context> contexts, String permission, Tristate tristate) {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_SET_PERMISSION)) {
if (tristate == Tristate.UNDEFINED) {
// Unset
Node.Builder builder = new me.lucko.luckperms.common.core.Node.Builder(s);
Node.Builder builder = new me.lucko.luckperms.common.core.Node.Builder(permission);
for (Context ct : set) {
for (Context ct : contexts) {
builder.withExtraContext(ct.getKey(), ct.getValue());
}
@ -123,10 +122,10 @@ public class LuckPermsSubjectData implements SubjectData {
return true;
}
Node.Builder builder = new me.lucko.luckperms.common.core.Node.Builder(s)
Node.Builder builder = new me.lucko.luckperms.common.core.Node.Builder(permission)
.setValue(tristate.asBoolean());
for (Context ct : set) {
for (Context ct : contexts) {
builder.withExtraContext(ct.getKey(), ct.getValue());
}
@ -141,9 +140,11 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return true;
}
}
@Override
public boolean clearPermissions() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_PERMISSIONS)) {
if (enduring) {
holder.clearNodes();
} else {
@ -152,12 +153,27 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return true;
}
}
@Override
public boolean clearPermissions(Set<Context> contexts) {
List<Node> toRemove = (enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(node -> node.shouldApplyWithContext(LuckPermsService.convertContexts(contexts)))
.collect(Collectors.toList());
public boolean clearPermissions(Set<Context> c) {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_PERMISSIONS)) {
List<Node> toRemove = new ArrayList<>();
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
Set<Context> contexts = LuckPermsService.convertContexts(n.getContexts());
if (n.isServerSpecific()) {
contexts.add(new Context(LuckPermsService.SERVER_CONTEXT, n.getServer().get()));
}
if (n.isWorldSpecific()) {
contexts.add(new Context(Context.WORLD_KEY, n.getWorld().get()));
}
if (contexts.equals(c)) {
toRemove.add(n);
}
}
toRemove.forEach(n -> {
try {
@ -176,9 +192,11 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return !toRemove.isEmpty();
}
}
@Override
public Map<Set<Context>, List<Subject>> getAllParents() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_GET_PARENTS)) {
Map<Set<Context>, List<Subject>> parents = new HashMap<>();
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
@ -209,21 +227,16 @@ public class LuckPermsSubjectData implements SubjectData {
}
return map.build();
}
}
@Override
public List<Subject> getParents(Set<Context> contexts) {
ImmutableList.Builder<Subject> parents = ImmutableList.builder();
(enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(Node::isGroupNode)
.filter(n -> n.shouldApplyWithContext(LuckPermsService.convertContexts(contexts), true))
.forEach(n -> parents.add(service.getGroupSubjects().get(n.getGroupName())));
return parents.build();
return getAllParents().getOrDefault(contexts, ImmutableList.of());
}
@Override
public boolean addParent(Set<Context> set, Subject subject) {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_ADD_PARENT)) {
if (subject instanceof LuckPermsGroupSubject) {
LuckPermsGroupSubject permsSubject = ((LuckPermsGroupSubject) subject);
ContextSet contexts = LuckPermsService.convertContexts(set);
@ -245,9 +258,11 @@ public class LuckPermsSubjectData implements SubjectData {
}
return false;
}
}
@Override
public boolean removeParent(Set<Context> set, Subject subject) {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_REMOVE_PARENT)) {
if (subject instanceof LuckPermsGroupSubject) {
LuckPermsGroupSubject permsSubject = ((LuckPermsGroupSubject) subject);
ContextSet contexts = LuckPermsService.convertContexts(set);
@ -269,9 +284,11 @@ public class LuckPermsSubjectData implements SubjectData {
}
return false;
}
}
@Override
public boolean clearParents() {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_PARENTS)) {
List<Node> toRemove = (enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(Node::isGroupNode)
.collect(Collectors.toList());
@ -293,15 +310,31 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return !toRemove.isEmpty();
}
}
@Override
public boolean clearParents(Set<Context> set) {
ContextSet context = LuckPermsService.convertContexts(set);
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_PARENTS)) {
List<Node> toRemove = new ArrayList<>();
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
if (!n.isGroupNode()) {
continue;
}
List<Node> toRemove = (enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(Node::isGroupNode)
.filter(node -> node.shouldApplyWithContext(context))
.collect(Collectors.toList());
Set<Context> contexts = LuckPermsService.convertContexts(n.getContexts());
if (n.isServerSpecific()) {
contexts.add(new Context(LuckPermsService.SERVER_CONTEXT, n.getServer().get()));
}
if (n.isWorldSpecific()) {
contexts.add(new Context(Context.WORLD_KEY, n.getWorld().get()));
}
if (contexts.equals(set)) {
toRemove.add(n);
}
}
toRemove.forEach(n -> {
try {
@ -320,9 +353,11 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return !toRemove.isEmpty();
}
}
@Override
public Map<Set<Context>, Map<String, String>> getAllOptions() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_GET_OPTIONS)) {
Map<Set<Context>, Map<String, String>> options = new HashMap<>();
int prefixPriority = Integer.MIN_VALUE;
@ -381,57 +416,16 @@ public class LuckPermsSubjectData implements SubjectData {
}
return map.build();
}
}
@Override
public Map<String, String> getOptions(Set<Context> set) {
ImmutableMap.Builder<String, String> options = ImmutableMap.builder();
ContextSet contexts = LuckPermsService.convertContexts(set);
int prefixPriority = Integer.MIN_VALUE;
int suffixPriority = Integer.MIN_VALUE;
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
if (!n.getValue()) {
continue;
}
if (!n.isMeta() || !n.isPrefix() || n.isSuffix()) {
continue;
}
if (!n.shouldApplyWithContext(contexts, true)) {
continue;
}
if (n.isPrefix()) {
Map.Entry<Integer, String> value = n.getPrefix();
if (value.getKey() > prefixPriority) {
options.put("prefix", value.getValue());
prefixPriority = value.getKey();
}
continue;
}
if (n.isSuffix()) {
Map.Entry<Integer, String> value = n.getSuffix();
if (value.getKey() > suffixPriority) {
options.put("suffix", value.getValue());
suffixPriority = value.getKey();
}
continue;
}
if (n.isMeta()) {
Map.Entry<String, String> meta = n.getMeta();
options.put(meta.getKey(), meta.getValue());
}
}
return options.build();
return getAllOptions().getOrDefault(set, ImmutableMap.of());
}
@Override
public boolean setOption(Set<Context> set, String key, String value) {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_SET_OPTION)) {
ContextSet context = LuckPermsService.convertContexts(set);
key = escapeCharacters(key);
@ -453,15 +447,31 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return true;
}
}
@Override
public boolean clearOptions(Set<Context> set) {
ContextSet context = LuckPermsService.convertContexts(set);
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_OPTIONS)) {
List<Node> toRemove = new ArrayList<>();
for (Node n : enduring ? holder.getNodes() : holder.getTransientNodes()) {
if (!n.isMeta() && !n.isPrefix() && !n.isSuffix()) {
continue;
}
List<Node> toRemove = (enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(n -> n.isMeta() || n.isPrefix() || n.isSuffix())
.filter(node -> node.shouldApplyWithContext(context))
.collect(Collectors.toList());
Set<Context> contexts = LuckPermsService.convertContexts(n.getContexts());
if (n.isServerSpecific()) {
contexts.add(new Context(LuckPermsService.SERVER_CONTEXT, n.getServer().get()));
}
if (n.isWorldSpecific()) {
contexts.add(new Context(Context.WORLD_KEY, n.getWorld().get()));
}
if (contexts.equals(set)) {
toRemove.add(n);
}
}
toRemove.forEach(n -> {
try {
@ -476,9 +486,11 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return !toRemove.isEmpty();
}
}
@Override
public boolean clearOptions() {
try (Timing i = service.getPlugin().getTimings().time(LPTiming.LP_SUBJECT_CLEAR_OPTIONS)) {
List<Node> toRemove = (enduring ? holder.getNodes() : holder.getTransientNodes()).stream()
.filter(n -> n.isMeta() || n.isPrefix() || n.isSuffix())
.collect(Collectors.toList());
@ -496,4 +508,5 @@ public class LuckPermsSubjectData implements SubjectData {
objectSave(holder);
return !toRemove.isEmpty();
}
}
}

View File

@ -22,6 +22,7 @@
package me.lucko.luckperms.sponge.service;
import co.aikar.timings.Timing;
import com.google.common.collect.ImmutableList;
import lombok.AccessLevel;
import lombok.EqualsAndHashCode;
@ -29,6 +30,7 @@ import lombok.Getter;
import me.lucko.luckperms.api.caching.MetaData;
import me.lucko.luckperms.api.context.ContextSet;
import me.lucko.luckperms.common.users.User;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.Sponge;
import org.spongepowered.api.command.CommandSource;
import org.spongepowered.api.entity.living.player.Player;
@ -61,15 +63,6 @@ public class LuckPermsUserSubject extends LuckPermsSubject {
this.transientSubjectData = new LuckPermsSubjectData(false, service, user);
}
public void deprovision() {
/* For some reason, Sponge holds onto User instances in a cache, which in turn, prevents LuckPerms data from being GCed.
As well as unloading, we also remove all references to the User instances. */
user = null;
service = null;
subjectData = null;
transientSubjectData = null;
}
private boolean hasData() {
return user.getUserData() != null;
}
@ -98,18 +91,25 @@ public class LuckPermsUserSubject extends LuckPermsSubject {
@Override
public Tristate getPermissionValue(ContextSet contexts, String permission) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_GET_PERMISSION_VALUE)) {
return !hasData() ?
Tristate.UNDEFINED :
LuckPermsService.convertTristate(user.getUserData().getPermissionData(service.calculateContexts(contexts)).getPermissionValue(permission));
LuckPermsService.convertTristate(
user.getUserData().getPermissionData(service.calculateContexts(contexts)).getPermissionValue(permission)
);
}
}
@Override
public boolean isChildOf(ContextSet contexts, Subject parent) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_IS_CHILD_OF)) {
return parent instanceof LuckPermsGroupSubject && getPermissionValue(contexts, "group." + parent.getIdentifier()).asBoolean();
}
}
@Override
public List<Subject> getParents(ContextSet contexts) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_GET_PARENTS)) {
ImmutableList.Builder<Subject> subjects = ImmutableList.builder();
if (hasData()) {
@ -130,9 +130,11 @@ public class LuckPermsUserSubject extends LuckPermsSubject {
return subjects.build();
}
}
@Override
public Optional<String> getOption(ContextSet contexts, String s) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_GET_OPTION)) {
if (hasData()) {
MetaData data = user.getUserData().getMetaData(service.calculateContexts(contexts));
if (s.equalsIgnoreCase("prefix")) {
@ -159,9 +161,12 @@ public class LuckPermsUserSubject extends LuckPermsSubject {
return service.getDefaults().getOption(LuckPermsService.convertContexts(contexts), s);
}
}
@Override
public ContextSet getActiveContextSet() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_GET_ACTIVE_CONTEXTS)) {
return service.getPlugin().getContextManager().getApplicableContext(this);
}
}
}

View File

@ -22,6 +22,7 @@
package me.lucko.luckperms.sponge.service.collections;
import co.aikar.timings.Timing;
import lombok.NonNull;
import me.lucko.luckperms.api.context.ContextSet;
import me.lucko.luckperms.common.groups.GroupManager;
@ -29,6 +30,7 @@ import me.lucko.luckperms.common.utils.ImmutableCollectors;
import me.lucko.luckperms.sponge.service.LuckPermsGroupSubject;
import me.lucko.luckperms.sponge.service.LuckPermsService;
import me.lucko.luckperms.sponge.service.simple.SimpleCollection;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.permission.PermissionService;
import org.spongepowered.api.service.permission.Subject;
@ -58,12 +60,14 @@ public class GroupCollection implements SubjectCollection {
@Override
public Subject get(@NonNull String id) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.GROUP_COLLECTION_GET)) {
if (manager.isLoaded(id)) {
return LuckPermsGroupSubject.wrapGroup(manager.get(id), service);
}
return fallback.get(id);
}
}
@Override
public boolean hasRegistered(@NonNull String id) {

View File

@ -22,11 +22,13 @@
package me.lucko.luckperms.sponge.service.collections;
import co.aikar.timings.Timing;
import com.google.common.cache.CacheBuilder;
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.UncheckedExecutionException;
import lombok.NonNull;
import me.lucko.luckperms.api.context.ContextSet;
import me.lucko.luckperms.common.commands.Util;
@ -36,6 +38,7 @@ import me.lucko.luckperms.common.utils.ImmutableCollectors;
import me.lucko.luckperms.sponge.service.LuckPermsService;
import me.lucko.luckperms.sponge.service.LuckPermsUserSubject;
import me.lucko.luckperms.sponge.service.simple.SimpleCollection;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.permission.PermissionService;
import org.spongepowered.api.service.permission.Subject;
@ -71,7 +74,7 @@ public class UserCollection implements SubjectCollection {
public LuckPermsUserSubject load(UUID uuid) throws Exception {
User user = manager.get(uuid);
if (user == null) {
throw new IllegalStateException("user not loaded");
throw new IllegalStateException("User not loaded");
}
return LuckPermsUserSubject.wrapUser(user, service);
@ -100,6 +103,7 @@ public class UserCollection implements SubjectCollection {
@Override
public Subject get(@NonNull String id) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.USER_COLLECTION_GET)) {
Optional<Subject> s = getIfLoaded(id);
if (s.isPresent()) {
return s.get();
@ -108,6 +112,7 @@ public class UserCollection implements SubjectCollection {
// Fallback to the other collection. This Subject instance will never be persisted.
return fallback.get(id);
}
}
private Optional<Subject> getIfLoaded(String id) {
UUID uuid = Util.parseUuid(id);
@ -135,7 +140,7 @@ public class UserCollection implements SubjectCollection {
UUID internal = service.getPlugin().getUuidCache().getUUID(uuid);
try {
return Optional.of(users.get(internal));
} catch (ExecutionException e) {
} catch (ExecutionException | UncheckedExecutionException e) {
return Optional.empty();
}
}

View File

@ -22,11 +22,13 @@
package me.lucko.luckperms.sponge.service.persisted;
import co.aikar.timings.Timing;
import com.google.common.collect.ImmutableList;
import lombok.Getter;
import lombok.NonNull;
import me.lucko.luckperms.common.utils.BufferedRequest;
import me.lucko.luckperms.sponge.service.LuckPermsService;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.command.CommandSource;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.permission.MemorySubjectData;
@ -95,6 +97,7 @@ public class PersistedSubject implements Subject {
@Override
public Tristate getPermissionValue(@NonNull Set<Context> contexts, @NonNull String node) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.PERSISTED_SUBJECT_GET_PERMISSION_VALUE)) {
Tristate res = subjectData.getNodeTree(contexts).get(node);
if (res != Tristate.UNDEFINED) {
return res;
@ -124,9 +127,11 @@ public class PersistedSubject implements Subject {
res = service.getDefaults().getPermissionValue(contexts, node);
return res;
}
}
@Override
public boolean isChildOf(@NonNull Set<Context> contexts, @NonNull Subject subject) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.PERSISTED_SUBJECT_IS_CHILD_OF)) {
if (getContainingCollection().getIdentifier().equalsIgnoreCase("defaults")) {
return subjectData.getParents(contexts).contains(subject) ||
transientSubjectData.getParents(contexts).contains(subject);
@ -137,9 +142,11 @@ public class PersistedSubject implements Subject {
service.getDefaults().getParents(contexts).contains(subject);
}
}
}
@Override
public List<Subject> getParents(@NonNull Set<Context> contexts) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.PERSISTED_SUBJECT_GET_PARENTS)) {
List<Subject> s = new ArrayList<>();
s.addAll(subjectData.getParents(contexts));
s.addAll(transientSubjectData.getParents(contexts));
@ -151,9 +158,11 @@ public class PersistedSubject implements Subject {
return ImmutableList.copyOf(s);
}
}
@Override
public Optional<String> getOption(Set<Context> set, String key) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.PERSISTED_SUBJECT_GET_OPTION)) {
Optional<String> res = Optional.ofNullable(subjectData.getOptions(getActiveContexts()).get(key));
if (res.isPresent()) {
return res;
@ -182,9 +191,12 @@ public class PersistedSubject implements Subject {
return service.getDefaults().getOption(set, key);
}
}
@Override
public Set<Context> getActiveContexts() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.PERSISTED_SUBJECT_GET_ACTIVE_CONTEXTS)) {
return LuckPermsService.convertContexts(service.getPlugin().getContextManager().getApplicableContext(this));
}
}
}

View File

@ -22,10 +22,12 @@
package me.lucko.luckperms.sponge.service.simple;
import co.aikar.timings.Timing;
import com.google.common.collect.ImmutableList;
import lombok.Getter;
import lombok.NonNull;
import me.lucko.luckperms.sponge.service.LuckPermsService;
import me.lucko.luckperms.sponge.timings.LPTiming;
import org.spongepowered.api.command.CommandSource;
import org.spongepowered.api.service.context.Context;
import org.spongepowered.api.service.permission.MemorySubjectData;
@ -74,6 +76,7 @@ public class SimpleSubject implements Subject {
@Override
public Tristate getPermissionValue(@NonNull Set<Context> contexts, @NonNull String node) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.SIMPLE_SUBJECT_GET_PERMISSION_VALUE)) {
Tristate res = subjectData.getNodeTree(contexts).get(node);
if (res != Tristate.UNDEFINED) {
return res;
@ -98,9 +101,11 @@ public class SimpleSubject implements Subject {
res = service.getDefaults().getPermissionValue(contexts, node);
return res;
}
}
@Override
public boolean isChildOf(@NonNull Set<Context> contexts, @NonNull Subject subject) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.SIMPLE_SUBJECT_IS_CHILD_OF)) {
if (getContainingCollection().getIdentifier().equalsIgnoreCase("defaults")) {
return subjectData.getParents(contexts).contains(subject);
} else {
@ -109,9 +114,11 @@ public class SimpleSubject implements Subject {
service.getDefaults().getParents(contexts).contains(subject);
}
}
}
@Override
public List<Subject> getParents(@NonNull Set<Context> contexts) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.SIMPLE_SUBJECT_GET_PARENTS)) {
List<Subject> s = new ArrayList<>();
s.addAll(subjectData.getParents(contexts));
@ -122,9 +129,11 @@ public class SimpleSubject implements Subject {
return ImmutableList.copyOf(s);
}
}
@Override
public Optional<String> getOption(Set<Context> set, String key) {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.SIMPLE_SUBJECT_GET_OPTION)) {
Optional<String> res = Optional.ofNullable(subjectData.getOptions(getActiveContexts()).get(key));
if (res.isPresent()) {
return res;
@ -148,9 +157,12 @@ public class SimpleSubject implements Subject {
return service.getDefaults().getOption(set, key);
}
}
@Override
public Set<Context> getActiveContexts() {
try (Timing ignored = service.getPlugin().getTimings().time(LPTiming.SIMPLE_SUBJECT_GET_ACTIVE_CONTEXTS)) {
return LuckPermsService.convertContexts(service.getPlugin().getContextManager().getApplicableContext(this));
}
}
}

View File

@ -0,0 +1,79 @@
/*
* Copyright (c) 2016 Lucko (Luck) <luck@lucko.me>
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
package me.lucko.luckperms.sponge.timings;
import lombok.AllArgsConstructor;
import lombok.Getter;
@Getter
@AllArgsConstructor
public enum LPTiming {
GET_SUBJECTS("getSubjects"),
USER_COLLECTION_GET("userCollectionGet"),
GROUP_COLLECTION_GET("groupCollectionGet"),
USER_GET_PERMISSION_VALUE("userGetPermissionValue"),
USER_GET_PARENTS("userGetParents"),
USER_IS_CHILD_OF("userIsChildOf"),
USER_GET_OPTION("userGetOption"),
USER_GET_ACTIVE_CONTEXTS("userGetActiveContexts"),
GROUP_GET_PERMISSION_VALUE("groupGetPermissionValue"),
GROUP_GET_PARENTS("groupGetParents"),
GROUP_IS_CHILD_OF("groupIsChildOf"),
GROUP_GET_OPTION("groupGetOption"),
GROUP_GET_ACTIVE_CONTEXTS("groupGetActiveContexts"),
LP_SUBJECT_GET_PERMISSIONS("lpSubjectGetPermissions"),
LP_SUBJECT_SET_PERMISSION("lpSubjectSetPermission"),
LP_SUBJECT_CLEAR_PERMISSIONS("lpSubjectClearPermissions"),
LP_SUBJECT_GET_PARENTS("lpSubjectGetParents"),
LP_SUBJECT_ADD_PARENT("lpSubjectAddParent"),
LP_SUBJECT_REMOVE_PARENT("lpSubjectRemoveParent"),
LP_SUBJECT_CLEAR_PARENTS("lpSubjectClearParents"),
LP_SUBJECT_GET_OPTIONS("lpSubjectGetOptions"),
LP_SUBJECT_SET_OPTION("lpSubjectSetOption"),
LP_SUBJECT_CLEAR_OPTIONS("lpSubjectClearOptions"),
SIMPLE_SUBJECT_GET_PERMISSION_VALUE("simpleSubjectGetPermissionValue"),
SIMPLE_SUBJECT_IS_CHILD_OF("simpleSubjectIsChildOf"),
SIMPLE_SUBJECT_GET_PARENTS("simpleSubjectGetParents"),
SIMPLE_SUBJECT_GET_OPTION("simpleSubjectGetOption"),
SIMPLE_SUBJECT_GET_ACTIVE_CONTEXTS("simpleSubjectGetActiveContexts"),
PERSISTED_SUBJECT_GET_PERMISSION_VALUE("persistedSubjectGetPermissionValue"),
PERSISTED_SUBJECT_IS_CHILD_OF("persistedSubjectIsChildOf"),
PERSISTED_SUBJECT_GET_PARENTS("persistedSubjectGetParents"),
PERSISTED_SUBJECT_GET_OPTION("persistedSubjectGetOption"),
PERSISTED_SUBJECT_GET_ACTIVE_CONTEXTS("persistedSubjectGetActiveContexts"),
ON_COMMAND("onCommand"),
COMMAND_TAB_COMPLETE("commandTabComplete"),
ON_CLIENT_LOGIN("onClientLogin"),
ON_CLIENT_LEAVE("onClientLeave");
private final String id;
}

View File

@ -0,0 +1,50 @@
/*
* Copyright (c) 2016 Lucko (Luck) <luck@lucko.me>
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
package me.lucko.luckperms.sponge.timings;
import co.aikar.timings.Timing;
import co.aikar.timings.Timings;
import com.google.common.collect.ImmutableMap;
import lombok.NonNull;
import me.lucko.luckperms.sponge.LPSpongePlugin;
import java.util.Map;
public class LPTimings {
private final Map<LPTiming, Timing> timings;
public LPTimings(LPSpongePlugin plugin) {
ImmutableMap.Builder<LPTiming, Timing> map = ImmutableMap.builder();
for (LPTiming t : LPTiming.values()) {
map.put(t, Timings.of(plugin, t.getId()));
}
timings = map.build();
}
public Timing time(@NonNull LPTiming timing) {
Timing t = timings.get(timing);
t.startTimingIfSync();
return t;
}
}