001/* 002 * PlotSquared, a land and world management plugin for Minecraft. 003 * Copyright (C) IntellectualSites <https://intellectualsites.com> 004 * Copyright (C) IntellectualSites team and contributors 005 * 006 * This program is free software: you can redistribute it and/or modify 007 * it under the terms of the GNU General Public License as published by 008 * the Free Software Foundation, either version 3 of the License, or 009 * (at your option) any later version. 010 * 011 * This program is distributed in the hope that it will be useful, 012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 014 * GNU General Public License for more details. 015 * 016 * You should have received a copy of the GNU General Public License 017 * along with this program. If not, see <https://www.gnu.org/licenses/>. 018 */ 019package com.plotsquared.core.uuid; 020 021import com.google.common.cache.Cache; 022import com.google.common.cache.CacheBuilder; 023import org.checkerframework.checker.nullness.qual.NonNull; 024import org.checkerframework.checker.nullness.qual.Nullable; 025 026import java.util.ArrayList; 027import java.util.Collection; 028import java.util.Collections; 029import java.util.List; 030import java.util.UUID; 031import java.util.function.Consumer; 032 033/** 034 * UUID service backed by a Guava Cache 035 */ 036public class CacheUUIDService implements UUIDService, Consumer<List<UUIDMapping>> { 037 038 private final Cache<String, UUIDMapping> usernameCache; 039 private final Cache<UUID, UUIDMapping> uuidCache; 040 041 /** 042 * Construct a new Cache UUID service with a maximum number of entries. 043 * Because it stores the mappings in two ways, the actual number 044 * of entries is two times the specified size 045 * 046 * @param size Maximum number of entries 047 */ 048 public CacheUUIDService(final int size) { 049 this.usernameCache = CacheBuilder.newBuilder().maximumSize(size).build(); 050 this.uuidCache = CacheBuilder.newBuilder().maximumSize(size).build(); 051 } 052 053 @Override 054 public @NonNull List<UUIDMapping> getNames(final @NonNull List<@NonNull UUID> uuids) { 055 final List<UUIDMapping> mappings = new ArrayList<>(uuids.size()); 056 mappings.addAll(this.uuidCache.getAllPresent(uuids).values()); 057 return mappings; 058 } 059 060 @Override 061 public @NonNull List<UUIDMapping> getUUIDs(final @NonNull List<@NonNull String> usernames) { 062 final List<UUIDMapping> mappings = new ArrayList<>(usernames.size()); 063 mappings.addAll(this.usernameCache.getAllPresent(usernames).values()); 064 return mappings; 065 } 066 067 @Override 068 public void accept(final @NonNull List<@NonNull UUIDMapping> uuidMappings) { 069 for (final UUIDMapping mapping : uuidMappings) { 070 this.uuidCache.put(mapping.uuid(), mapping); 071 this.usernameCache.put(mapping.username(), mapping); 072 } 073 } 074 075 @Override 076 public @NonNull Collection<@NonNull UUIDMapping> getImmediately() { 077 return this.usernameCache.asMap().values(); 078 } 079 080 @Override 081 public boolean canBeSynchronous() { 082 return true; 083 } 084 085 @Override 086 public @Nullable UUIDMapping getImmediately(final @NonNull Object object) { 087 final List<UUIDMapping> list; 088 if (object instanceof String) { 089 list = getUUIDs(Collections.singletonList((String) object)); 090 } else if (object instanceof UUID) { 091 list = getNames(Collections.singletonList((UUID) object)); 092 } else { 093 list = Collections.emptyList(); 094 } 095 if (list.isEmpty()) { 096 return null; 097 } 098 return list.get(0); 099 } 100 101}