Add RegistryAccess for managing registries

This commit is contained in:
Jake Potrebic 2022-03-02 13:36:21 -08:00
parent 41efb5322e
commit 25c065b4b2
12 changed files with 238 additions and 79 deletions

View file

@ -0,0 +1,47 @@
package io.papermc.paper.registry;
import org.bukkit.Keyed;
import org.bukkit.NamespacedKey;
import org.bukkit.Registry;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
/**
* Represents a reference to a server-backed registry value that may
* change.
*
* @param <T> type of the value
*/
@Deprecated(forRemoval = true, since = "1.20.6")
public interface Reference<T extends Keyed> extends Keyed {
/**
* Gets the value from the registry with the key.
*
* @return the value
* @throws java.util.NoSuchElementException if there is no value with this key
*/
@Deprecated(forRemoval = true, since = "1.20.6")
@NotNull T value();
/**
* Gets the value from the registry with the key.
*
* @return the value or null if it doesn't exist
*/
@Deprecated(forRemoval = true, since = "1.20.6")
@Nullable T valueOrNull();
/**
* Creates a reference to a registered value.
*
* @param registry the registry the value is located in
* @param key the key to the value
* @param <T> the type of the value
* @return a reference
*/
@Deprecated(forRemoval = true, since = "1.20.6")
static <T extends Keyed> @NotNull Reference<T> create(@NotNull Registry<T> registry, @NotNull NamespacedKey key) {
return new ReferenceImpl<>(registry, key);
}
}

View file

@ -0,0 +1,31 @@
package io.papermc.paper.registry;
import org.bukkit.Keyed;
import org.bukkit.NamespacedKey;
import org.bukkit.Registry;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.NoSuchElementException;
record ReferenceImpl<T extends Keyed>(@NotNull Registry<T> registry, @NotNull NamespacedKey key) implements Reference<T> {
@Override
public @NotNull T value() {
final T value = this.registry.get(this.key);
if (value == null) {
throw new NoSuchElementException("No such value with key " + this.key);
}
return value;
}
@Override
public @Nullable T valueOrNull() {
return this.registry.get(this.key);
}
@Override
public @NotNull NamespacedKey getKey() {
return this.key;
}
}

View file

@ -0,0 +1,50 @@
package io.papermc.paper.registry;
import org.bukkit.Keyed;
import org.bukkit.Registry;
import org.jetbrains.annotations.ApiStatus;
import org.jspecify.annotations.NullMarked;
import org.jspecify.annotations.Nullable;
/**
* Used for accessing different {@link Registry} instances
* by a {@link RegistryKey}. Get the main instance of {@link RegistryAccess}
* with {@link RegistryAccess#registryAccess()}.
*/
@NullMarked
@ApiStatus.NonExtendable
public interface RegistryAccess {
/**
* Get the {@link RegistryAccess} instance for the server.
*
* @return the RegistryAccess instance
*/
static RegistryAccess registryAccess() {
return RegistryAccessHolder.INSTANCE.orElseThrow(() -> new IllegalStateException("No RegistryAccess implementation found"));
}
/**
* Gets the registry based on the type.
*
* @param type the type
* @return the registry or null if none found
* @param <T> the type
* @deprecated use {@link #getRegistry(RegistryKey)} with keys from {@link RegistryKey}
*/
@Deprecated(since = "1.20.6", forRemoval = true)
<T extends Keyed> @Nullable Registry<T> getRegistry(Class<T> type);
/**
* Gets the registry with the specified key.
*
* @param registryKey the key
* @return the registry
* @param <T> the type
* @throws java.util.NoSuchElementException if no registry with the key is found
* @throws IllegalArgumentException if the registry is not available yet
*/
// Future note: We should have no trouble removing this generic qualifier when
// registry types no longer have to be "keyed" as it shouldn't break ABI or API.
<T extends Keyed> Registry<T> getRegistry(RegistryKey<T> registryKey);
}

View file

@ -0,0 +1,12 @@
package io.papermc.paper.registry;
import java.util.Optional;
import java.util.ServiceLoader;
final class RegistryAccessHolder {
static final Optional<RegistryAccess> INSTANCE = ServiceLoader.load(RegistryAccess.class).findFirst();
private RegistryAccessHolder() {
}
}

View file

@ -12,6 +12,17 @@ record RegistryKeyImpl<T>(Key key) implements RegistryKey<T> {
static final Set<RegistryKey<?>> REGISTRY_KEYS = Sets.newIdentityHashSet(); static final Set<RegistryKey<?>> REGISTRY_KEYS = Sets.newIdentityHashSet();
// override equals and hashCode to this can be used to simulate an "identity" hashmap
@Override
public boolean equals(final @Nullable Object obj) {
return obj == this;
}
@Override
public int hashCode() {
return System.identityHashCode(this);
}
static <T> RegistryKey<T> create(@Subst("some_key") final String key) { static <T> RegistryKey<T> create(@Subst("some_key") final String key) {
final RegistryKey<T> registryKey = createInternal(key); final RegistryKey<T> registryKey = createInternal(key);
REGISTRY_KEYS.add(registryKey); REGISTRY_KEYS.add(registryKey);

View file

@ -2434,8 +2434,11 @@ public final class Bukkit {
* @param tClass of the registry to get * @param tClass of the registry to get
* @param <T> type of the registry * @param <T> type of the registry
* @return the corresponding registry or null if not present * @return the corresponding registry or null if not present
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)}
* with keys from {@link io.papermc.paper.registry.RegistryKey}
*/ */
@Nullable @Nullable
@Deprecated(since = "1.20.6")
public static <T extends Keyed> Registry<T> getRegistry(@NotNull Class<T> tClass) { public static <T extends Keyed> Registry<T> getRegistry(@NotNull Class<T> tClass) {
return server.getRegistry(tClass); return server.getRegistry(tClass);
} }

View file

@ -163,28 +163,23 @@ public enum Particle implements Keyed {
private final NamespacedKey key; private final NamespacedKey key;
private final Class<?> dataType; private final Class<?> dataType;
final boolean register; // Paper - all particles are registered
Particle(String key) { Particle(String key) {
this(key, Void.class); this(key, Void.class);
} }
Particle(String key, boolean register) { // Paper - all particles are registered
this(key, Void.class, register);
}
Particle(String key, /*@NotNull*/ Class<?> data) { Particle(String key, /*@NotNull*/ Class<?> data) {
this(key, data, true); // Paper - all particles are registered
}
Particle(String key, /*@NotNull*/ Class<?> data, boolean register) {
if (key != null) { if (key != null) {
this.key = NamespacedKey.minecraft(key); this.key = NamespacedKey.minecraft(key);
} else { } else {
this.key = null; this.key = null;
} }
dataType = data; dataType = data;
this.register = register; // Paper - all particles are registered
} }
/** /**

View file

@ -86,26 +86,32 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* Server art. * Server art.
* *
* @see Art * @see Art
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#PAINTING_VARIANT}
*/ */
Registry<Art> ART = Objects.requireNonNull(Bukkit.getRegistry(Art.class), "No registry present for Art. This is a bug."); @Deprecated(since = "1.21.3") // Paper
Registry<Art> ART = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(Art.class), "No registry present for Art. This is a bug.");
/** /**
* Attribute. * Attribute.
* *
* @see Attribute * @see Attribute
*/ */
Registry<Attribute> ATTRIBUTE = Objects.requireNonNull(Bukkit.getRegistry(Attribute.class), "No registry present for Attribute. This is a bug."); Registry<Attribute> ATTRIBUTE = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.ATTRIBUTE); // Paper
/** /**
* Server banner patterns. * Server banner patterns.
* *
* @see PatternType * @see PatternType
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#BANNER_PATTERN}
*/ */
Registry<PatternType> BANNER_PATTERN = Objects.requireNonNull(Bukkit.getRegistry(PatternType.class), "No registry present for Pattern Type. This is a bug."); @Deprecated(since = "1.21") // Paper
Registry<PatternType> BANNER_PATTERN = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(PatternType.class), "No registry present for PatternType. This is a bug."); // Paper
/** /**
* Server biomes. * Server biomes.
* *
* @see Biome * @see Biome
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#BIOME}
*/ */
Registry<Biome> BIOME = Objects.requireNonNull(Bukkit.getRegistry(Biome.class), "No registry present for Biome. This is a bug."); @Deprecated(since = "1.21.3") // Paper
Registry<Biome> BIOME = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(Biome.class), "No registry present for Biome. This is a bug.");
/** /**
* Server block types. * Server block types.
* *
@ -113,7 +119,7 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* @apiNote BlockType is not ready for public usage yet * @apiNote BlockType is not ready for public usage yet
*/ */
@ApiStatus.Internal @ApiStatus.Internal
Registry<BlockType> BLOCK = Objects.requireNonNull(Bukkit.getRegistry(BlockType.class), "No registry present for BlockType. This is a bug."); Registry<BlockType> BLOCK = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.BLOCK); // Paper
/** /**
* Custom boss bars. * Custom boss bars.
* *
@ -155,25 +161,29 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* *
* @see Cat.Type * @see Cat.Type
*/ */
Registry<Cat.Type> CAT_VARIANT = Objects.requireNonNull(Bukkit.getRegistry(Cat.Type.class), "No registry present for Cat Type. This is a bug."); Registry<Cat.Type> CAT_VARIANT = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.CAT_VARIANT); // Paper
/** /**
* Server enchantments. * Server enchantments.
* *
* @see Enchantment * @see Enchantment
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#ENCHANTMENT}
*/ */
Registry<Enchantment> ENCHANTMENT = Objects.requireNonNull(Bukkit.getRegistry(Enchantment.class), "No registry present for Enchantment. This is a bug."); @Deprecated(since = "1.21")
Registry<Enchantment> ENCHANTMENT = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(Enchantment.class), "No registry present for Enchantment. This is a bug."); // Paper
/** /**
* Server entity types. * Server entity types.
* *
* @see EntityType * @see EntityType
*/ */
Registry<EntityType> ENTITY_TYPE = new SimpleRegistry<>(EntityType.class, (entity) -> entity != EntityType.UNKNOWN); Registry<EntityType> ENTITY_TYPE = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.ENTITY_TYPE); // Paper
/** /**
* Server instruments. * Server instruments.
* *
* @see MusicInstrument * @see MusicInstrument
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#INSTRUMENT}
*/ */
Registry<MusicInstrument> INSTRUMENT = Objects.requireNonNull(Bukkit.getRegistry(MusicInstrument.class), "No registry present for MusicInstrument. This is a bug."); @Deprecated(since = "1.21.2")
Registry<MusicInstrument> INSTRUMENT = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(MusicInstrument.class), "No registry present for Instruments. This is a bug."); // Paper
/** /**
* Server item types. * Server item types.
* *
@ -181,7 +191,7 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* @apiNote ItemType is not ready for public usage yet * @apiNote ItemType is not ready for public usage yet
*/ */
@ApiStatus.Internal @ApiStatus.Internal
Registry<ItemType> ITEM = Objects.requireNonNull(Bukkit.getRegistry(ItemType.class), "No registry present for ItemType. This is a bug."); Registry<ItemType> ITEM = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.ITEM); // Paper
/** /**
* Default server loot tables. * Default server loot tables.
* *
@ -200,25 +210,25 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* @see MenuType * @see MenuType
*/ */
@ApiStatus.Experimental @ApiStatus.Experimental
Registry<MenuType> MENU = Objects.requireNonNull(Bukkit.getRegistry(MenuType.class), "No registry present for MenuType. This is a bug."); Registry<MenuType> MENU = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.MENU); // Paper
/** /**
* Server mob effects. * Server mob effects.
* *
* @see PotionEffectType * @see PotionEffectType
*/ */
Registry<PotionEffectType> EFFECT = Objects.requireNonNull(Bukkit.getRegistry(PotionEffectType.class), "No registry present for PotionEffectType. This is a bug."); Registry<PotionEffectType> EFFECT = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.MOB_EFFECT); // Paper
/** /**
* Server particles. * Server particles.
* *
* @see Particle * @see Particle
*/ */
Registry<Particle> PARTICLE_TYPE = new SimpleRegistry<>(Particle.class, (par) -> par.register); Registry<Particle> PARTICLE_TYPE = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.PARTICLE_TYPE); // Paper
/** /**
* Server potions. * Server potions.
* *
* @see PotionType * @see PotionType
*/ */
Registry<PotionType> POTION = new SimpleRegistry<>(PotionType.class); Registry<PotionType> POTION = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.POTION); // Paper
/** /**
* Server statistics. * Server statistics.
* *
@ -229,58 +239,67 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* Server structures. * Server structures.
* *
* @see Structure * @see Structure
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#STRUCTURE}
*/ */
Registry<Structure> STRUCTURE = Objects.requireNonNull(Bukkit.getRegistry(Structure.class), "No registry present for Structure. This is a bug."); @Deprecated(since = "1.20.6") // Paper
Registry<Structure> STRUCTURE = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(Structure.class), "No registry present for Structure. This is a bug."); // Paper
/** /**
* Server structure types. * Server structure types.
* *
* @see StructureType * @see StructureType
*/ */
Registry<StructureType> STRUCTURE_TYPE = Objects.requireNonNull(Bukkit.getRegistry(StructureType.class), "No registry present for StructureType. This is a bug."); Registry<StructureType> STRUCTURE_TYPE = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.STRUCTURE_TYPE), "No registry present for StructureType. This is a bug."); // Paper
/** /**
* Sound keys. * Sound keys.
* *
* @see Sound * @see Sound
*/ */
Registry<Sound> SOUNDS = Objects.requireNonNull(Bukkit.getRegistry(Sound.class), "No registry present for Sound. This is a bug."); Registry<Sound> SOUNDS = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.SOUND_EVENT); // Paper
/** /**
* Trim materials. * Trim materials.
* *
* @see TrimMaterial * @see TrimMaterial
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#TRIM_MATERIAL}
*/ */
Registry<TrimMaterial> TRIM_MATERIAL = Objects.requireNonNull(Bukkit.getRegistry(TrimMaterial.class), "No registry present for TrimMaterial. This is a bug."); @Deprecated(since = "1.20.6") // Paper
Registry<TrimMaterial> TRIM_MATERIAL = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(TrimMaterial.class), "No registry present for TrimMaterial. This is a bug."); // Paper
/** /**
* Trim patterns. * Trim patterns.
* *
* @see TrimPattern * @see TrimPattern
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#TRIM_PATTERN}
*/ */
Registry<TrimPattern> TRIM_PATTERN = Objects.requireNonNull(Bukkit.getRegistry(TrimPattern.class), "No registry present for TrimPattern. This is a bug."); @Deprecated(since = "1.20.6")
Registry<TrimPattern> TRIM_PATTERN = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(TrimPattern.class), "No registry present for TrimPattern. This is a bug."); // Paper
/** /**
* Damage types. * Damage types.
* *
* @see DamageType * @see DamageType
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#DAMAGE_TYPE}
*/ */
@ApiStatus.Experimental @Deprecated(since = "1.20.6")
Registry<DamageType> DAMAGE_TYPE = Objects.requireNonNull(Bukkit.getRegistry(DamageType.class), "No registry present for DamageType. This is a bug."); Registry<DamageType> DAMAGE_TYPE = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(DamageType.class), "No registry present for DamageType. This is a bug."); // Paper
/** /**
* Jukebox songs. * Jukebox songs.
* *
* @see JukeboxSong * @see JukeboxSong
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#JUKEBOX_SONG}
*/ */
@ApiStatus.Experimental @ApiStatus.Experimental
Registry<JukeboxSong> JUKEBOX_SONG = Objects.requireNonNull(Bukkit.getRegistry(JukeboxSong.class), "No registry present for JukeboxSong. This is a bug."); @Deprecated(since = "1.21")
Registry<JukeboxSong> JUKEBOX_SONG = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(JukeboxSong.class), "No registry present for JukeboxSong. This is a bug."); // Paper
/** /**
* Villager profession. * Villager profession.
* *
* @see Villager.Profession * @see Villager.Profession
*/ */
Registry<Villager.Profession> VILLAGER_PROFESSION = Objects.requireNonNull(Bukkit.getRegistry(Villager.Profession.class), "No registry present for Villager Profession. This is a bug."); Registry<Villager.Profession> VILLAGER_PROFESSION = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.VILLAGER_PROFESSION); // Paper
/** /**
* Villager type. * Villager type.
* *
* @see Villager.Type * @see Villager.Type
*/ */
Registry<Villager.Type> VILLAGER_TYPE = Objects.requireNonNull(Bukkit.getRegistry(Villager.Type.class), "No registry present for Villager Type. This is a bug."); Registry<Villager.Type> VILLAGER_TYPE = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.VILLAGER_TYPE); // Paper
/** /**
* Memory Keys. * Memory Keys.
* *
@ -321,31 +340,33 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
* *
* @see Fluid * @see Fluid
*/ */
Registry<Fluid> FLUID = Objects.requireNonNull(Bukkit.getRegistry(Fluid.class), "No registry present for Fluid. This is a bug."); Registry<Fluid> FLUID = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.FLUID); // Paper
/** /**
* Frog variants. * Frog variants.
* *
* @see Frog.Variant * @see Frog.Variant
*/ */
Registry<Frog.Variant> FROG_VARIANT = Objects.requireNonNull(Bukkit.getRegistry(Frog.Variant.class), "No registry present for Frog Variant. This is a bug."); Registry<Frog.Variant> FROG_VARIANT = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.FROG_VARIANT); // Paper
/** /**
* Wolf variants. * Wolf variants.
* *
* @see Wolf.Variant * @see Wolf.Variant
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)} with {@link io.papermc.paper.registry.RegistryKey#WOLF_VARIANT}
*/ */
Registry<Wolf.Variant> WOLF_VARIANT = Objects.requireNonNull(Bukkit.getRegistry(Wolf.Variant.class), "No registry present for Wolf Variant. This is a bug."); @Deprecated(since = "1.20.6")
Registry<Wolf.Variant> WOLF_VARIANT = Objects.requireNonNull(io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(Wolf.Variant.class), "No registry present for Wolf$Variant. This is a bug."); // Paper
/** /**
* Map cursor types. * Map cursor types.
* *
* @see MapCursor.Type * @see MapCursor.Type
*/ */
Registry<MapCursor.Type> MAP_DECORATION_TYPE = Objects.requireNonNull(Bukkit.getRegistry(MapCursor.Type.class), "No registry present for MapCursor Type. This is a bug."); Registry<MapCursor.Type> MAP_DECORATION_TYPE = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.MAP_DECORATION_TYPE); // Paper
/** /**
* Game events. * Game events.
* *
* @see GameEvent * @see GameEvent
*/ */
Registry<GameEvent> GAME_EVENT = Objects.requireNonNull(Bukkit.getRegistry(GameEvent.class), "No registry present for GameEvent. This is a bug."); Registry<GameEvent> GAME_EVENT = io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(io.papermc.paper.registry.RegistryKey.GAME_EVENT); // Paper
/** /**
* Get the object by its key. * Get the object by its key.
* *
@ -396,7 +417,7 @@ public interface Registry<T extends Keyed> extends Iterable<T> {
return (namespacedKey != null) ? get(namespacedKey) : null; return (namespacedKey != null) ? get(namespacedKey) : null;
} }
static final class SimpleRegistry<T extends Enum<T> & Keyed> implements Registry<T> { class SimpleRegistry<T extends Enum<T> & Keyed> implements Registry<T> { // Paper - remove final
private final Class<T> type; private final Class<T> type;
private final Map<NamespacedKey, T> map; private final Map<NamespacedKey, T> map;

View file

@ -2077,8 +2077,11 @@ public interface Server extends PluginMessageRecipient, net.kyori.adventure.audi
* @param tClass of the registry to get * @param tClass of the registry to get
* @param <T> type of the registry * @param <T> type of the registry
* @return the corresponding registry or null if not present * @return the corresponding registry or null if not present
* @deprecated use {@link io.papermc.paper.registry.RegistryAccess#getRegistry(io.papermc.paper.registry.RegistryKey)}
* with keys from {@link io.papermc.paper.registry.RegistryKey}
*/ */
@Nullable @Nullable
@Deprecated(since = "1.20.6") // Paper
<T extends Keyed> Registry<T> getRegistry(@NotNull Class<T> tClass); <T extends Keyed> Registry<T> getRegistry(@NotNull Class<T> tClass);
/** /**

View file

@ -0,0 +1,20 @@
package io.papermc.paper.registry;
import org.bukkit.Keyed;
import org.bukkit.Registry;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class TestRegistryAccess implements RegistryAccess {
@Override
@Deprecated(since = "1.20.6", forRemoval = true)
public @Nullable <T extends Keyed> Registry<T> getRegistry(final @NotNull Class<T> type) {
throw new UnsupportedOperationException("Not supported");
}
@Override
public @NotNull <T extends Keyed> Registry<T> getRegistry(final @NotNull RegistryKey<T> registryKey) {
throw new UnsupportedOperationException("Not supported");
}
}

View file

@ -38,46 +38,11 @@ public final class TestServer {
when(instance.getBukkitVersion()).thenReturn("BukkitVersion_" + TestServer.class.getPackage().getImplementationVersion()); when(instance.getBukkitVersion()).thenReturn("BukkitVersion_" + TestServer.class.getPackage().getImplementationVersion());
Map<Class<? extends Keyed>, Registry<?>> registers = new HashMap<>(); // Paper start - RegistryAccess
when(instance.getRegistry(any())).then(invocationOnMock -> registers.computeIfAbsent(invocationOnMock.getArgument(0), aClass -> new Registry<>() { when(instance.getRegistry(any())).then(invocationOnMock -> {
private final Map<NamespacedKey, Keyed> cache = new HashMap<>(); return io.papermc.paper.registry.RegistryAccess.registryAccess().getRegistry(((Class<Keyed>)invocationOnMock.getArgument(0)));
});
@Override // Paper end - RegistryAccess
public Keyed get(NamespacedKey key) {
Class<? extends Keyed> theClass;
// Some registries have extra Typed classes such as BlockType and ItemType.
// To avoid class cast exceptions during init mock the Typed class.
// To get the correct class, we just use the field type.
try {
theClass = (Class<? extends Keyed>) aClass.getField(key.getKey().toUpperCase(Locale.ROOT).replace('.', '_')).getType();
} catch (ClassCastException | NoSuchFieldException e) {
throw new RuntimeException(e);
}
return cache.computeIfAbsent(key, key2 -> mock(theClass, withSettings().stubOnly()));
}
@NotNull
@Override
public Keyed getOrThrow(@NotNull NamespacedKey key) {
Keyed keyed = get(key);
Preconditions.checkArgument(keyed != null, "No %s registry entry found for key %s.", aClass, key);
return keyed;
}
@NotNull
@Override
public Stream<Keyed> stream() {
throw new UnsupportedOperationException("Not supported");
}
@Override
public Iterator<Keyed> iterator() {
throw new UnsupportedOperationException("Not supported");
}
}));
UnsafeValues unsafeValues = mock(withSettings().stubOnly()); UnsafeValues unsafeValues = mock(withSettings().stubOnly());
when(instance.getUnsafe()).thenReturn(unsafeValues); when(instance.getUnsafe()).thenReturn(unsafeValues);

View file

@ -0,0 +1 @@
io.papermc.paper.registry.TestRegistryAccess