Archiviert
13
0

Update to 1.13.1, rework cloning, fix a particle NPE

Dieser Commit ist enthalten in:
Dan Mulloy 2018-09-15 14:32:18 -04:00
Ursprung 8ec31d83db
Commit 776ec56a2d
25 geänderte Dateien mit 205 neuen und 182 gelöschten Zeilen

Datei anzeigen

@ -21,20 +21,14 @@ import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Map.Entry; import java.util.Map.Entry;
import java.util.function.Function;
import java.util.function.Supplier;
import com.comphenix.protocol.reflect.EquivalentConverter; import com.comphenix.protocol.reflect.EquivalentConverter;
import com.comphenix.protocol.reflect.StructureModifier; import com.comphenix.protocol.reflect.StructureModifier;
import com.comphenix.protocol.utility.MinecraftReflection; import com.comphenix.protocol.utility.MinecraftReflection;
import com.comphenix.protocol.utility.MinecraftVersion; import com.comphenix.protocol.wrappers.*;
import com.comphenix.protocol.wrappers.BlockPosition;
import com.comphenix.protocol.wrappers.BukkitConverters;
import com.comphenix.protocol.wrappers.ChunkPosition;
import com.comphenix.protocol.wrappers.MinecraftKey;
import com.comphenix.protocol.wrappers.WrappedBlockData;
import com.comphenix.protocol.wrappers.WrappedDataWatcher;
import com.comphenix.protocol.wrappers.WrappedServerPing;
import com.comphenix.protocol.wrappers.nbt.NbtFactory; import com.comphenix.protocol.wrappers.nbt.NbtFactory;
import com.comphenix.protocol.wrappers.nbt.NbtWrapper;
import com.google.common.collect.Maps; import com.google.common.collect.Maps;
/** /**
@ -43,62 +37,56 @@ import com.google.common.collect.Maps;
* @author Kristian * @author Kristian
*/ */
public class BukkitCloner implements Cloner { public class BukkitCloner implements Cloner {
// List of classes we support private static final Map<Class<?>, Function<Object, Object>> CLONERS = Maps.newConcurrentMap();
private final Map<Integer, Class<?>> clonableClasses = Maps.newConcurrentMap();
public BukkitCloner() { private static void fromWrapper(Supplier<Class<?>> getClass, Function<Object, ClonableWrapper> fromHandle) {
addClass(0, MinecraftReflection.getItemStackClass());
addClass(1, MinecraftReflection.getDataWatcherClass());
// Try to add position classes
try { try {
addClass(2, MinecraftReflection.getBlockPositionClass()); Class<?> nmsClass = getClass.get();
} catch (Throwable ex) { if (nmsClass != null) {
CLONERS.put(nmsClass, nmsObject -> fromHandle.apply(nmsObject).deepClone().getHandle());
}
} catch (RuntimeException ignored) { }
} }
private static void fromConverter(Supplier<Class<?>> getClass, EquivalentConverter converter) {
try { try {
addClass(3, MinecraftReflection.getChunkPositionClass()); Class<?> nmsClass = getClass.get();
} catch (Throwable ex) { if (nmsClass != null) {
} CLONERS.put(nmsClass, nmsObject -> converter.getGeneric(converter.getSpecific(nmsObject)));
}
if (MinecraftReflection.isUsingNetty()) { } catch (RuntimeException ignored) { }
addClass(4, MinecraftReflection.getServerPingClass());
}
if (MinecraftReflection.watcherObjectExists()) {
addClass(5, MinecraftReflection.getDataWatcherSerializerClass());
addClass(6, MinecraftReflection.getMinecraftKeyClass());
} }
private static void fromManual(Supplier<Class<?>> getClass, Function<Object, Object> cloner) {
try { try {
addClass(7, MinecraftReflection.getIBlockDataClass()); Class<?> nmsClass = getClass.get();
} catch (Throwable ex) { if (nmsClass != null) {
CLONERS.put(nmsClass, cloner);
}
} catch (RuntimeException ignored) { }
} }
try { static {
addClass(8, MinecraftReflection.getNonNullListClass()); fromManual(MinecraftReflection::getItemStackClass, source ->
} catch (Throwable ex) { MinecraftReflection.getMinecraftItemStack(MinecraftReflection.getBukkitItemStack(source).clone()));
fromWrapper(MinecraftReflection::getDataWatcherClass, WrappedDataWatcher::new);
fromConverter(MinecraftReflection::getBlockPositionClass, BlockPosition.getConverter());
fromConverter(MinecraftReflection::getChunkPositionClass, ChunkPosition.getConverter());
fromWrapper(MinecraftReflection::getServerPingClass, WrappedServerPing::fromHandle);
fromConverter(MinecraftReflection::getMinecraftKeyClass, MinecraftKey.getConverter());
fromWrapper(MinecraftReflection::getIBlockDataClass, WrappedBlockData::fromHandle);
fromManual(MinecraftReflection::getNonNullListClass, source -> nonNullListCloner().clone(source));
fromWrapper(MinecraftReflection::getNBTBaseClass, NbtFactory::fromNMS);
} }
try { private Function<Object, Object> findCloner(Class<?> type) {
addClass(9, MinecraftReflection.getNBTBaseClass()); for (Entry<Class<?>, Function<Object, Object>> entry : CLONERS.entrySet()) {
} catch (Throwable ex) { } if (entry.getKey().isAssignableFrom(type)) {
} return entry.getValue();
private void addClass(int id, Class<?> clazz) {
if (clazz != null)
clonableClasses.put(id, clazz);
}
private int findMatchingClass(Class<?> type) {
// See if is a subclass of any of our supported superclasses
for (Entry<Integer, Class<?>> entry : clonableClasses.entrySet()) {
if (entry.getValue().isAssignableFrom(type)) {
return entry.getKey();
} }
} }
return -1; return null;
} }
@Override @Override
@ -106,7 +94,7 @@ public class BukkitCloner implements Cloner {
if (source == null) if (source == null)
return false; return false;
return findMatchingClass(source.getClass()) >= 0; return findCloner(source.getClass()) != null;
} }
@Override @Override
@ -114,43 +102,12 @@ public class BukkitCloner implements Cloner {
if (source == null) if (source == null)
throw new IllegalArgumentException("source cannot be NULL."); throw new IllegalArgumentException("source cannot be NULL.");
// Convert to a wrapper return findCloner(source.getClass()).apply(source);
switch (findMatchingClass(source.getClass())) {
case 0:
return MinecraftReflection.getMinecraftItemStack(MinecraftReflection.getBukkitItemStack(source).clone());
case 1:
EquivalentConverter<WrappedDataWatcher> dataConverter = BukkitConverters.getDataWatcherConverter();
return dataConverter.getGeneric(dataConverter.getSpecific(source).deepClone());
case 2:
EquivalentConverter<BlockPosition> blockConverter = BlockPosition.getConverter();
return blockConverter.getGeneric(blockConverter.getSpecific(source));
case 3:
EquivalentConverter<ChunkPosition> chunkConverter = ChunkPosition.getConverter();
return chunkConverter.getGeneric(chunkConverter.getSpecific(source));
case 4:
EquivalentConverter<WrappedServerPing> serverConverter = BukkitConverters.getWrappedServerPingConverter();
return serverConverter.getGeneric(serverConverter.getSpecific(source).deepClone());
case 5:
return source;
case 6:
EquivalentConverter<MinecraftKey> keyConverter = MinecraftKey.getConverter();
return keyConverter.getGeneric(keyConverter.getSpecific(source));
case 7:
EquivalentConverter<WrappedBlockData> blockDataConverter = BukkitConverters.getWrappedBlockDataConverter();
return blockDataConverter.getGeneric(blockDataConverter.getSpecific(source).deepClone());
case 8:
return nonNullListCloner().clone(source);
case 9:
NbtWrapper<?> clone = (NbtWrapper<?>) NbtFactory.fromNMS(source).deepClone();
return clone.getHandle();
default:
throw new IllegalArgumentException("Cannot clone objects of type " + source.getClass());
}
} }
private static Constructor<?> nonNullList = null; private static Constructor<?> nonNullList = null;
private static final Cloner nonNullListCloner() { private static Cloner nonNullListCloner() {
return new Cloner() { return new Cloner() {
@Override @Override
public boolean canClone(Object source) { public boolean canClone(Object source) {

Datei anzeigen

@ -26,11 +26,15 @@ import java.net.URI;
import java.net.URL; import java.net.URL;
import java.security.PublicKey; import java.security.PublicKey;
import java.util.Locale; import java.util.Locale;
import java.util.Set;
import java.util.UUID; import java.util.UUID;
import java.util.function.Supplier;
import javax.crypto.SecretKey; import javax.crypto.SecretKey;
import com.comphenix.protocol.utility.MinecraftReflection; import com.comphenix.protocol.utility.MinecraftReflection;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Sets;
import com.google.common.primitives.Primitives; import com.google.common.primitives.Primitives;
/** /**
@ -42,19 +46,41 @@ import com.google.common.primitives.Primitives;
*/ */
public class ImmutableDetector implements Cloner { public class ImmutableDetector implements Cloner {
// Notable immutable classes we might encounter // Notable immutable classes we might encounter
private static final Class<?>[] immutableClasses = { private static final Set<Class<?>> immutableClasses = ImmutableSet.of(
StackTraceElement.class, BigDecimal.class, StackTraceElement.class, BigDecimal.class,
BigInteger.class, Locale.class, UUID.class, BigInteger.class, Locale.class, UUID.class,
URL.class, URI.class, Inet4Address.class, URL.class, URI.class, Inet4Address.class,
Inet6Address.class, InetSocketAddress.class, Inet6Address.class, InetSocketAddress.class,
SecretKey.class, PublicKey.class SecretKey.class, PublicKey.class
}; );
private static final Set<Class<?>> immutableNMS = Sets.newConcurrentHashSet();
static {
add(MinecraftReflection::getGameProfileClass);
add(MinecraftReflection::getDataWatcherSerializerClass);
add(() -> MinecraftReflection.getMinecraftClass("SoundEffect"));
add(MinecraftReflection::getBlockClass);
add(MinecraftReflection::getItemClass);
add(MinecraftReflection::getFluidTypeClass);
add(MinecraftReflection::getParticleTypeClass);
}
private static void add(Supplier<Class<?>> getClass) {
try {
Class<?> clazz = getClass.get();
if (clazz != null) {
immutableNMS.add(clazz);
}
} catch (RuntimeException ignored) { }
}
@Override @Override
public boolean canClone(Object source) { public boolean canClone(Object source) {
// Don't accept NULL // Don't accept NULL
if (source == null) if (source == null) {
return false; return false;
}
return isImmutable(source.getClass()); return isImmutable(source.getClass());
} }
@ -66,46 +92,35 @@ public class ImmutableDetector implements Cloner {
*/ */
public static boolean isImmutable(Class<?> type) { public static boolean isImmutable(Class<?> type) {
// Cases that are definitely not true // Cases that are definitely not true
if (type.isArray()) if (type.isArray()) {
return false; return false;
}
// All primitive types // All primitive types
if (Primitives.isWrapperType(type) || String.class.equals(type)) if (Primitives.isWrapperType(type) || String.class.equals(type)) {
return true; return true;
}
// May not be true, but if so, that kind of code is broken anyways // May not be true, but if so, that kind of code is broken anyways
if (isEnumWorkaround(type)) if (isEnumWorkaround(type)) {
return true;
for (Class<?> clazz : immutableClasses)
if (clazz.equals(type))
return true;
// Check for known immutable classes in 1.7.2
if (MinecraftReflection.isUsingNetty()) {
if (type.equals(MinecraftReflection.getGameProfileClass())) {
return true;
}
}
// Check for known immutable classes in 1.9
if (MinecraftReflection.watcherObjectExists()) {
if (type.equals(MinecraftReflection.getDataWatcherSerializerClass())
|| type.equals(MinecraftReflection.getMinecraftClass("SoundEffect"))) {
return true;
}
}
if (MinecraftReflection.is(MinecraftReflection.getBlockClass(), type)
|| MinecraftReflection.is(MinecraftReflection.getItemClass(), type)
|| MinecraftReflection.is(MinecraftReflection.getFluidTypeClass(), type)) {
return true; return true;
} }
// No good way to clone lambdas
if (type.getName().contains("$$Lambda$")) { if (type.getName().contains("$$Lambda$")) {
return true; return true;
} }
if (immutableClasses.contains(type)) {
return true;
}
for (Class<?> clazz : immutableNMS) {
if (MinecraftReflection.is(clazz, type)) {
return true;
}
}
// Probably not // Probably not
return false; return false;
} }
@ -113,10 +128,13 @@ public class ImmutableDetector implements Cloner {
// This is just great. Just great. // This is just great. Just great.
private static boolean isEnumWorkaround(Class<?> enumClass) { private static boolean isEnumWorkaround(Class<?> enumClass) {
while (enumClass != null) { while (enumClass != null) {
if (enumClass.isEnum()) if (enumClass.isEnum()) {
return true; return true;
}
enumClass = enumClass.getSuperclass(); enumClass = enumClass.getSuperclass();
} }
return false; return false;
} }

Datei anzeigen

@ -48,6 +48,7 @@ public class MinecraftProtocolVersion {
map.put(new MinecraftVersion(1, 12, 1), 338); map.put(new MinecraftVersion(1, 12, 1), 338);
map.put(new MinecraftVersion(1, 12, 2), 340); map.put(new MinecraftVersion(1, 12, 2), 340);
map.put(new MinecraftVersion(1, 13, 0), 393); map.put(new MinecraftVersion(1, 13, 0), 393);
map.put(new MinecraftVersion(1, 13, 1), 401);
return map; return map;
} }

Datei anzeigen

@ -1156,6 +1156,10 @@ public class MinecraftReflection {
return getNullableNMS("FluidType"); return getNullableNMS("FluidType");
} }
public static Class<?> getParticleTypeClass() {
return getNullableNMS("ParticleType");
}
/** /**
* Retrieve the WorldType class. * Retrieve the WorldType class.
* @return The WorldType class. * @return The WorldType class.
@ -1360,7 +1364,7 @@ public class MinecraftReflection {
public static Class<?> getDataWatcherSerializerClass() { public static Class<?> getDataWatcherSerializerClass() {
// TODO Implement a fallback // TODO Implement a fallback
return getMinecraftClass("DataWatcherSerializer"); return getNullableNMS("DataWatcherSerializer");
} }
public static Class<?> getDataWatcherRegistryClass() { public static Class<?> getDataWatcherRegistryClass() {

Datei anzeigen

@ -0,0 +1,7 @@
package com.comphenix.protocol.wrappers;
public interface ClonableWrapper {
Object getHandle();
ClonableWrapper deepClone();
}

Datei anzeigen

@ -33,7 +33,7 @@ import org.bukkit.Material;
* @author dmulloy2 * @author dmulloy2
*/ */
public abstract class WrappedBlockData extends AbstractWrapper { public abstract class WrappedBlockData extends AbstractWrapper implements ClonableWrapper {
private static final Class<?> MAGIC_NUMBERS = MinecraftReflection.getCraftBukkitClass("util.CraftMagicNumbers"); private static final Class<?> MAGIC_NUMBERS = MinecraftReflection.getCraftBukkitClass("util.CraftMagicNumbers");
private static final Class<?> IBLOCK_DATA = MinecraftReflection.getIBlockDataClass(); private static final Class<?> IBLOCK_DATA = MinecraftReflection.getIBlockDataClass();
private static final Class<?> BLOCK = MinecraftReflection.getBlockClass(); private static final Class<?> BLOCK = MinecraftReflection.getBlockClass();

Datei anzeigen

@ -42,7 +42,7 @@ import org.bukkit.inventory.ItemStack;
* Represents a DataWatcher * Represents a DataWatcher
* @author dmulloy2 * @author dmulloy2
*/ */
public class WrappedDataWatcher extends AbstractWrapper implements Iterable<WrappedWatchableObject> { public class WrappedDataWatcher extends AbstractWrapper implements Iterable<WrappedWatchableObject>, ClonableWrapper {
private static final Class<?> HANDLE_TYPE = MinecraftReflection.getDataWatcherClass(); private static final Class<?> HANDLE_TYPE = MinecraftReflection.getDataWatcherClass();
private static MethodAccessor GETTER = null; private static MethodAccessor GETTER = null;

Datei anzeigen

@ -91,6 +91,8 @@ public class WrappedParticle<T> {
} }
public static WrappedParticle fromHandle(Object handle) { public static WrappedParticle fromHandle(Object handle) {
ensureMethods();
Particle bukkit = (Particle) toBukkit.invoke(null, handle); Particle bukkit = (Particle) toBukkit.invoke(null, handle);
Object data = null; Object data = null;

Datei anzeigen

@ -40,7 +40,7 @@ import io.netty.handler.codec.base64.Base64;
* Represents a server ping packet data. * Represents a server ping packet data.
* @author Kristian * @author Kristian
*/ */
public class WrappedServerPing extends AbstractWrapper { public class WrappedServerPing extends AbstractWrapper implements ClonableWrapper {
private static Class<?> GAME_PROFILE = MinecraftReflection.getGameProfileClass(); private static Class<?> GAME_PROFILE = MinecraftReflection.getGameProfileClass();
private static Class<?> GAME_PROFILE_ARRAY = MinecraftReflection.getArrayClass(GAME_PROFILE); private static Class<?> GAME_PROFILE_ARRAY = MinecraftReflection.getArrayClass(GAME_PROFILE);

Datei anzeigen

@ -18,6 +18,8 @@
package com.comphenix.protocol.wrappers.nbt; package com.comphenix.protocol.wrappers.nbt;
import com.comphenix.protocol.wrappers.ClonableWrapper;
/** /**
* Represents a generic container for an NBT element. * Represents a generic container for an NBT element.
* <p> * <p>
@ -26,7 +28,7 @@ package com.comphenix.protocol.wrappers.nbt;
* @author Kristian * @author Kristian
* @param <TType> - type of the value that is stored. * @param <TType> - type of the value that is stored.
*/ */
public interface NbtBase<TType> { public interface NbtBase<TType> extends ClonableWrapper {
/** /**
* Accepts a NBT visitor. * Accepts a NBT visitor.
* @param visitor - the hierarchical NBT visitor. * @param visitor - the hierarchical NBT visitor.
@ -84,4 +86,8 @@ public interface NbtBase<TType> {
* @return The cloned tag. * @return The cloned tag.
*/ */
public abstract NbtBase<TType> deepClone(); public abstract NbtBase<TType> deepClone();
default Object getHandle() {
return null;
}
} }

Datei anzeigen

@ -19,6 +19,8 @@ package com.comphenix.protocol.wrappers.nbt;
import java.io.DataOutput; import java.io.DataOutput;
import com.comphenix.protocol.wrappers.ClonableWrapper;
/** /**
* Indicates that this NBT wraps an underlying net.minecraft.server instance. * Indicates that this NBT wraps an underlying net.minecraft.server instance.
* <p> * <p>
@ -28,7 +30,7 @@ import java.io.DataOutput;
* *
* @param <TType> - type of the value that is stored. * @param <TType> - type of the value that is stored.
*/ */
public interface NbtWrapper<TType> extends NbtBase<TType> { public interface NbtWrapper<TType> extends NbtBase<TType>, ClonableWrapper {
/** /**
* Retrieve the underlying net.minecraft.server instance. * Retrieve the underlying net.minecraft.server instance.
* @return The NMS instance. * @return The NMS instance.

Datei anzeigen

@ -246,7 +246,7 @@
<dependency> <dependency>
<groupId>org.mockito</groupId> <groupId>org.mockito</groupId>
<artifactId>mockito-core</artifactId> <artifactId>mockito-core</artifactId>
<version>2.19.1</version> <version>2.21.0</version>
<scope>test</scope> <scope>test</scope>
</dependency> </dependency>
<dependency> <dependency>

Datei anzeigen

@ -51,11 +51,11 @@ import io.netty.channel.socket.SocketChannel;
import io.netty.handler.codec.ByteToMessageDecoder; import io.netty.handler.codec.ByteToMessageDecoder;
import io.netty.handler.codec.MessageToByteEncoder; import io.netty.handler.codec.MessageToByteEncoder;
import io.netty.util.AttributeKey; import io.netty.util.AttributeKey;
import io.netty.util.concurrent.GenericFutureListener;
import io.netty.util.internal.TypeParameterMatcher; import io.netty.util.internal.TypeParameterMatcher;
import net.sf.cglib.proxy.Factory; import net.sf.cglib.proxy.Factory;
import org.apache.commons.lang3.Validate;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
@ -478,7 +478,11 @@ public class ChannelInjector extends ByteToMessageDecoder implements Injector {
private void scheduleMainThread(final Object packetCopy) { private void scheduleMainThread(final Object packetCopy) {
// Don't use BukkitExecutors for this - it has a bit of overhead // Don't use BukkitExecutors for this - it has a bit of overhead
Bukkit.getScheduler().scheduleSyncDelayedTask(factory.getPlugin(), () -> invokeSendPacket(packetCopy)); Bukkit.getScheduler().scheduleSyncDelayedTask(factory.getPlugin(), () -> {
if (!closed) {
invokeSendPacket(packetCopy);
}
});
} }
@Override @Override
@ -644,6 +648,8 @@ public class ChannelInjector extends ByteToMessageDecoder implements Injector {
* @param packet - the packet to send. * @param packet - the packet to send.
*/ */
private void invokeSendPacket(Object packet) { private void invokeSendPacket(Object packet) {
Validate.isTrue(!closed, "cannot send packets to a closed channel");
// Attempt to send the packet with NetworkMarker.handle(), or the PlayerConnection if its active // Attempt to send the packet with NetworkMarker.handle(), or the PlayerConnection if its active
try { try {
if (player instanceof Factory) { if (player instanceof Factory) {
@ -694,8 +700,14 @@ public class ChannelInjector extends ByteToMessageDecoder implements Injector {
*/ */
private Object getPlayerConnection() { private Object getPlayerConnection() {
if (playerConnection == null) { if (playerConnection == null) {
playerConnection = MinecraftFields.getPlayerConnection(getPlayer()); Player player = getPlayer();
if (player == null) {
throw new IllegalStateException("cannot send packet to offline player" + (playerName != null ? " " + playerName : ""));
} }
playerConnection = MinecraftFields.getPlayerConnection(player);
}
return playerConnection; return playerConnection;
} }
@ -714,7 +726,7 @@ public class ChannelInjector extends ByteToMessageDecoder implements Injector {
@Override @Override
public Player getPlayer() { public Player getPlayer() {
if (player == null && playerName != null) { if (player == null && playerName != null) {
return Bukkit.getPlayer(playerName); return Bukkit.getPlayerExact(playerName);
} }
return player; return player;

Datei anzeigen

@ -4,14 +4,14 @@ import com.comphenix.protocol.utility.Constants;
import com.comphenix.protocol.utility.MinecraftReflection; import com.comphenix.protocol.utility.MinecraftReflection;
import com.comphenix.protocol.utility.MinecraftVersion; import com.comphenix.protocol.utility.MinecraftVersion;
import net.minecraft.server.v1_13_R1.DispenserRegistry; import net.minecraft.server.v1_13_R2.DispenserRegistry;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.Server; import org.bukkit.Server;
import org.bukkit.craftbukkit.v1_13_R1.CraftServer; import org.bukkit.craftbukkit.v1_13_R2.CraftServer;
import org.bukkit.craftbukkit.v1_13_R1.inventory.CraftItemFactory; import org.bukkit.craftbukkit.v1_13_R2.inventory.CraftItemFactory;
import org.bukkit.craftbukkit.v1_13_R1.util.Versioning; import org.bukkit.craftbukkit.v1_13_R2.util.Versioning;
import static org.mockito.Mockito.*; import static org.mockito.Mockito.*;
@ -21,13 +21,27 @@ import static org.mockito.Mockito.*;
* @author Kristian * @author Kristian
*/ */
public class BukkitInitialization { public class BukkitInitialization {
private static boolean initialized; private static final BukkitInitialization instance = new BukkitInitialization();
private static boolean packaged;
private BukkitInitialization() {
System.out.println("Created new BukkitInitialization on " + Thread.currentThread().getName());
}
private boolean initialized;
private boolean packaged;
public static synchronized void initializePackage() {
instance.setPackage();
}
public static synchronized void initializeItemMeta() {
instance.initialize();
}
/** /**
* Initialize Bukkit and ProtocolLib such that we can perfrom unit testing * Initialize Bukkit and ProtocolLib such that we can perfrom unit testing
*/ */
public static void initializeItemMeta() { private void initialize() {
if (!initialized) { if (!initialized) {
// Denote that we're done // Denote that we're done
initialized = true; initialized = true;
@ -62,7 +76,7 @@ public class BukkitInitialization {
/** /**
* Ensure that package names are correctly set up. * Ensure that package names are correctly set up.
*/ */
public static void initializePackage() { private void setPackage() {
if (!packaged) { if (!packaged) {
packaged = true; packaged = true;

Datei anzeigen

@ -25,9 +25,9 @@ import com.comphenix.protocol.PacketType.Protocol;
import com.comphenix.protocol.PacketType.Sender; import com.comphenix.protocol.PacketType.Sender;
import com.comphenix.protocol.injector.packet.PacketRegistry; import com.comphenix.protocol.injector.packet.PacketRegistry;
import net.minecraft.server.v1_13_R1.EnumProtocol; import net.minecraft.server.v1_13_R2.EnumProtocol;
import net.minecraft.server.v1_13_R1.EnumProtocolDirection; import net.minecraft.server.v1_13_R2.EnumProtocolDirection;
import net.minecraft.server.v1_13_R1.PacketLoginInStart; import net.minecraft.server.v1_13_R2.PacketLoginInStart;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Test; import org.junit.Test;

Datei anzeigen

@ -36,8 +36,8 @@ import com.comphenix.protocol.wrappers.nbt.NbtCompound;
import com.comphenix.protocol.wrappers.nbt.NbtFactory; import com.comphenix.protocol.wrappers.nbt.NbtFactory;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import net.minecraft.server.v1_13_R1.*; import net.minecraft.server.v1_13_R2.*;
import net.minecraft.server.v1_13_R1.PacketPlayOutUpdateAttributes.AttributeSnapshot; import net.minecraft.server.v1_13_R2.PacketPlayOutUpdateAttributes.AttributeSnapshot;
import org.apache.commons.lang.SerializationUtils; import org.apache.commons.lang.SerializationUtils;
import org.apache.commons.lang3.builder.EqualsBuilder; import org.apache.commons.lang3.builder.EqualsBuilder;

Datei anzeigen

@ -6,8 +6,8 @@ import static org.junit.Assert.assertEquals;
import java.util.Arrays; import java.util.Arrays;
import java.util.List; import java.util.List;
import net.minecraft.server.v1_13_R1.ItemStack; import net.minecraft.server.v1_13_R2.ItemStack;
import net.minecraft.server.v1_13_R1.NonNullList; import net.minecraft.server.v1_13_R2.NonNullList;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Test; import org.junit.Test;

Datei anzeigen

@ -6,22 +6,22 @@ import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.times; import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify; import static org.mockito.Mockito.verify;
import net.minecraft.server.v1_13_R1.ChatComponentText; import net.minecraft.server.v1_13_R2.ChatComponentText;
import net.minecraft.server.v1_13_R1.ChunkCoordIntPair; import net.minecraft.server.v1_13_R2.ChunkCoordIntPair;
import net.minecraft.server.v1_13_R1.DataWatcher; import net.minecraft.server.v1_13_R2.DataWatcher;
import net.minecraft.server.v1_13_R1.IBlockData; import net.minecraft.server.v1_13_R2.IBlockData;
import net.minecraft.server.v1_13_R1.IChatBaseComponent; import net.minecraft.server.v1_13_R2.IChatBaseComponent;
import net.minecraft.server.v1_13_R1.IChatBaseComponent.ChatSerializer; import net.minecraft.server.v1_13_R2.IChatBaseComponent.ChatSerializer;
import net.minecraft.server.v1_13_R1.NBTCompressedStreamTools; import net.minecraft.server.v1_13_R2.NBTCompressedStreamTools;
import net.minecraft.server.v1_13_R1.PacketPlayOutUpdateAttributes.AttributeSnapshot; import net.minecraft.server.v1_13_R2.PacketPlayOutUpdateAttributes.AttributeSnapshot;
import net.minecraft.server.v1_13_R1.PlayerConnection; import net.minecraft.server.v1_13_R2.PlayerConnection;
import net.minecraft.server.v1_13_R1.ServerPing; import net.minecraft.server.v1_13_R2.ServerPing;
import net.minecraft.server.v1_13_R1.ServerPing.ServerData; import net.minecraft.server.v1_13_R2.ServerPing.ServerData;
import net.minecraft.server.v1_13_R1.ServerPing.ServerPingPlayerSample; import net.minecraft.server.v1_13_R2.ServerPing.ServerPingPlayerSample;
import org.bukkit.Material; import org.bukkit.Material;
import org.bukkit.block.Block; import org.bukkit.block.Block;
import org.bukkit.craftbukkit.v1_13_R1.inventory.CraftItemStack; import org.bukkit.craftbukkit.v1_13_R2.inventory.CraftItemStack;
import org.bukkit.entity.Entity; import org.bukkit.entity.Entity;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.junit.AfterClass; import org.junit.AfterClass;

Datei anzeigen

@ -6,7 +6,7 @@ import com.comphenix.protocol.BukkitInitialization;
import com.comphenix.protocol.wrappers.nbt.NbtCompound; import com.comphenix.protocol.wrappers.nbt.NbtCompound;
import com.comphenix.protocol.wrappers.nbt.NbtFactory; import com.comphenix.protocol.wrappers.nbt.NbtFactory;
import net.minecraft.server.v1_13_R1.IntHashMap; import net.minecraft.server.v1_13_R2.IntHashMap;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
import org.bukkit.Material; import org.bukkit.Material;

Datei anzeigen

@ -16,14 +16,14 @@ public class ChunkCoordIntPairTest {
@Test @Test
public void test() { public void test() {
net.minecraft.server.v1_13_R1.ChunkCoordIntPair pair = new net.minecraft.server.v1_13_R1.ChunkCoordIntPair(1, 2); net.minecraft.server.v1_13_R2.ChunkCoordIntPair pair = new net.minecraft.server.v1_13_R2.ChunkCoordIntPair(1, 2);
ChunkCoordIntPair specific = ChunkCoordIntPair.getConverter().getSpecific(pair); ChunkCoordIntPair specific = ChunkCoordIntPair.getConverter().getSpecific(pair);
assertEquals(1, specific.getChunkX()); assertEquals(1, specific.getChunkX());
assertEquals(2, specific.getChunkZ()); assertEquals(2, specific.getChunkZ());
net.minecraft.server.v1_13_R1.ChunkCoordIntPair roundtrip = net.minecraft.server.v1_13_R2.ChunkCoordIntPair roundtrip =
(net.minecraft.server.v1_13_R1.ChunkCoordIntPair) ChunkCoordIntPair.getConverter(). (net.minecraft.server.v1_13_R2.ChunkCoordIntPair) ChunkCoordIntPair.getConverter().
getGeneric(specific); getGeneric(specific);
assertEquals(1, roundtrip.x); assertEquals(1, roundtrip.x);

Datei anzeigen

@ -2,12 +2,12 @@ package com.comphenix.protocol.wrappers;
import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertEquals;
import net.minecraft.server.v1_13_R1.EntityHuman.EnumChatVisibility; import net.minecraft.server.v1_13_R2.EntityHuman.EnumChatVisibility;
import net.minecraft.server.v1_13_R1.EnumDifficulty; import net.minecraft.server.v1_13_R2.EnumDifficulty;
import net.minecraft.server.v1_13_R1.EnumGamemode; import net.minecraft.server.v1_13_R2.EnumGamemode;
import net.minecraft.server.v1_13_R1.EnumProtocol; import net.minecraft.server.v1_13_R2.EnumProtocol;
import net.minecraft.server.v1_13_R1.PacketPlayInClientCommand.EnumClientCommand; import net.minecraft.server.v1_13_R2.PacketPlayInClientCommand.EnumClientCommand;
import net.minecraft.server.v1_13_R1.PacketPlayInUseEntity.EnumEntityUseAction; import net.minecraft.server.v1_13_R2.PacketPlayInUseEntity.EnumEntityUseAction;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Test; import org.junit.Test;

Datei anzeigen

@ -6,9 +6,9 @@ import static org.junit.Assert.assertTrue;
import java.util.List; import java.util.List;
import net.minecraft.server.v1_13_R1.AttributeModifier; import net.minecraft.server.v1_13_R2.AttributeModifier;
import net.minecraft.server.v1_13_R1.PacketPlayOutUpdateAttributes; import net.minecraft.server.v1_13_R2.PacketPlayOutUpdateAttributes;
import net.minecraft.server.v1_13_R1.PacketPlayOutUpdateAttributes.AttributeSnapshot; import net.minecraft.server.v1_13_R2.PacketPlayOutUpdateAttributes.AttributeSnapshot;
import org.junit.Before; import org.junit.Before;
import org.junit.BeforeClass; import org.junit.BeforeClass;

Datei anzeigen

@ -23,10 +23,10 @@ import com.comphenix.protocol.wrappers.WrappedDataWatcher.Registry;
import com.comphenix.protocol.wrappers.WrappedDataWatcher.Serializer; import com.comphenix.protocol.wrappers.WrappedDataWatcher.Serializer;
import com.comphenix.protocol.wrappers.WrappedDataWatcher.WrappedDataWatcherObject; import com.comphenix.protocol.wrappers.WrappedDataWatcher.WrappedDataWatcherObject;
import net.minecraft.server.v1_13_R1.EntityEgg; import net.minecraft.server.v1_13_R2.EntityEgg;
import org.bukkit.craftbukkit.v1_13_R1.entity.CraftEgg; import org.bukkit.craftbukkit.v1_13_R2.entity.CraftEgg;
import org.bukkit.craftbukkit.v1_13_R1.entity.CraftEntity; import org.bukkit.craftbukkit.v1_13_R2.entity.CraftEntity;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Test; import org.junit.Test;
@ -87,8 +87,8 @@ public class WrappedDataWatcherTest {
@Test @Test
public void testSerializers() { public void testSerializers() {
Serializer blockPos = Registry.get(net.minecraft.server.v1_13_R1.BlockPosition.class, false); Serializer blockPos = Registry.get(net.minecraft.server.v1_13_R2.BlockPosition.class, false);
Serializer optionalBlockPos = Registry.get(net.minecraft.server.v1_13_R1.BlockPosition.class, true); Serializer optionalBlockPos = Registry.get(net.minecraft.server.v1_13_R2.BlockPosition.class, true);
assertNotSame(blockPos, optionalBlockPos); assertNotSame(blockPos, optionalBlockPos);
// assertNull(Registry.get(ItemStack.class, false)); // assertNull(Registry.get(ItemStack.class, false));

Datei anzeigen

@ -26,8 +26,8 @@ import java.io.DataInputStream;
import java.io.DataOutput; import java.io.DataOutput;
import java.io.DataOutputStream; import java.io.DataOutputStream;
import net.minecraft.server.v1_13_R1.ItemStack; import net.minecraft.server.v1_13_R2.ItemStack;
import net.minecraft.server.v1_13_R1.Items; import net.minecraft.server.v1_13_R2.Items;
import org.junit.BeforeClass; import org.junit.BeforeClass;
import org.junit.Test; import org.junit.Test;

Datei anzeigen

@ -8,7 +8,7 @@
<properties> <properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<spigotVersion>1.13-R0.1-SNAPSHOT</spigotVersion> <spigotVersion>1.13.1-R0.1-SNAPSHOT</spigotVersion>
</properties> </properties>
<modules> <modules>