mirror of
https://github.com/GeyserMC/Geyser.git
synced 2024-08-14 23:57:35 +00:00
Merge remote-tracking branch 'origin/feature/floodgate-merge'
# Conflicts: # bootstrap/bungeecord/src/main/java/org/geysermc/geyser/platform/bungeecord/GeyserBungeePlugin.java # bootstrap/fabric/src/main/java/org/geysermc/geyser/platform/fabric/GeyserFabricMod.java # bootstrap/spigot/src/main/java/org/geysermc/geyser/platform/spigot/GeyserSpigotPlugin.java # bootstrap/sponge/src/main/java/org/geysermc/geyser/platform/sponge/GeyserSpongePlugin.java # bootstrap/standalone/src/main/java/org/geysermc/geyser/platform/standalone/GeyserStandaloneBootstrap.java # bootstrap/velocity/src/main/java/org/geysermc/geyser/platform/velocity/GeyserVelocityPlugin.java # core/build.gradle.kts # core/src/main/java/org/geysermc/geyser/GeyserImpl.java # core/src/main/java/org/geysermc/geyser/command/defaults/VersionCommand.java # core/src/main/java/org/geysermc/geyser/dump/DumpInfo.java # core/src/main/java/org/geysermc/geyser/entity/type/FireworkEntity.java # core/src/main/java/org/geysermc/geyser/network/netty/LocalSession.java # core/src/main/java/org/geysermc/geyser/session/GeyserSession.java # core/src/main/java/org/geysermc/geyser/translator/protocol/bedrock/BedrockCommandRequestTranslator.java # core/src/main/java/org/geysermc/geyser/translator/protocol/bedrock/BedrockNetworkStackLatencyTranslator.java # core/src/main/java/org/geysermc/geyser/translator/protocol/java/JavaCustomPayloadTranslator.java # core/src/main/java/org/geysermc/geyser/translator/protocol/java/level/JavaBlockUpdateTranslator.java # gradle/libs.versions.toml
This commit is contained in:
commit
6ca53f5bf3
56 changed files with 733 additions and 315 deletions
|
@ -2,6 +2,8 @@ dependencies {
|
||||||
api(projects.core)
|
api(projects.core)
|
||||||
|
|
||||||
implementation(libs.adventure.text.serializer.bungeecord)
|
implementation(libs.adventure.text.serializer.bungeecord)
|
||||||
|
|
||||||
|
implementation("org.geysermc.floodgate", "bungee", "2.2.0-SNAPSHOT")
|
||||||
}
|
}
|
||||||
|
|
||||||
platformRelocate("net.md_5.bungee.jni")
|
platformRelocate("net.md_5.bungee.jni")
|
||||||
|
|
|
@ -0,0 +1,101 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2019-2022 GeyserMC. http://geysermc.org
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* @author GeyserMC
|
||||||
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.geysermc.geyser.platform.bungeecord;
|
||||||
|
|
||||||
|
import net.md_5.bungee.api.plugin.Listener;
|
||||||
|
|
||||||
|
public final class BungeeHybridListener implements Listener {
|
||||||
|
// // TODO consolidate with Floodgate
|
||||||
|
// private static final Field CHANNEL_WRAPPER;
|
||||||
|
// private static final Field PLAYER_NAME;
|
||||||
|
//
|
||||||
|
// static {
|
||||||
|
// CHANNEL_WRAPPER =
|
||||||
|
// ReflectionUtils.getFieldOfType(InitialHandler.class, ChannelWrapper.class);
|
||||||
|
// checkNotNull(CHANNEL_WRAPPER, "ChannelWrapper field cannot be null");
|
||||||
|
//
|
||||||
|
// PLAYER_NAME = ReflectionUtils.getField(InitialHandler.class, "name");
|
||||||
|
// checkNotNull(PLAYER_NAME, "Initial name field cannot be null");
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @EventHandler(priority = EventPriority.LOWEST)
|
||||||
|
// public void onPreLogin(PreLoginEvent event) {
|
||||||
|
// // well, no reason to check if the player will be kicked anyway
|
||||||
|
// if (event.isCancelled()) {
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// PendingConnection connection = event.getConnection();
|
||||||
|
// Connection player = getPlayer(connection);
|
||||||
|
// if (player != null) {
|
||||||
|
// connection.setOnlineMode(false);
|
||||||
|
// connection.setUniqueId(player.javaUuid());
|
||||||
|
// ReflectionUtils.setValue(connection, PLAYER_NAME, player.javaUsername());
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @EventHandler(priority = EventPriority.LOW)
|
||||||
|
// public void onServerConnect(ServerConnectEvent event) {
|
||||||
|
// boolean sendFloodgateData = false; // TODO
|
||||||
|
// if (!sendFloodgateData) {
|
||||||
|
// return; // TODO just don't register event?
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// PendingConnection connection = event.getPlayer().getPendingConnection();
|
||||||
|
// Connection player = getPlayer(connection);
|
||||||
|
// if (player != null) {
|
||||||
|
// Handshake handshake = ReflectionUtils.getCastedValue(connection, "handshake");
|
||||||
|
// BedrockData data = ((FloodgateConnection) player).toBedrockData(); // FIXME
|
||||||
|
// String encryptedData = ((ProxyHybridProvider) GeyserImpl.getInstance().getHybridProvider())
|
||||||
|
// .createEncryptedDataString(data);
|
||||||
|
//
|
||||||
|
// String address = handshake.getHost();
|
||||||
|
//
|
||||||
|
// // our data goes before all the other data
|
||||||
|
// int addressFinished = address.indexOf('\0');
|
||||||
|
// String originalAddress;
|
||||||
|
// String remaining;
|
||||||
|
// if (addressFinished != -1) {
|
||||||
|
// originalAddress = address.substring(0, addressFinished);
|
||||||
|
// remaining = address.substring(addressFinished);
|
||||||
|
// } else {
|
||||||
|
// originalAddress = address;
|
||||||
|
// remaining = "";
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// handshake.setHost(originalAddress + '\0' + encryptedData + remaining);
|
||||||
|
// // Bungeecord will add its data after our data
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Nullable
|
||||||
|
// private Connection getPlayer(PendingConnection connection) {
|
||||||
|
// ChannelWrapper wrapper = ReflectionUtils.getCastedValue(connection, CHANNEL_WRAPPER);
|
||||||
|
// Channel channel = wrapper.getHandle();
|
||||||
|
//
|
||||||
|
// return channel.attr(IntegratedHybridProvider.SESSION_KEY).get(); // TODO re-use Floodgate's attribute key here?
|
||||||
|
// }
|
||||||
|
}
|
|
@ -40,6 +40,7 @@ public final class GeyserBungeeConfiguration extends GeyserJacksonConfiguration
|
||||||
@JsonIgnore
|
@JsonIgnore
|
||||||
private Path floodgateKeyPath;
|
private Path floodgateKeyPath;
|
||||||
|
|
||||||
|
// TODO remove
|
||||||
public void loadFloodgate(GeyserBungeePlugin plugin) {
|
public void loadFloodgate(GeyserBungeePlugin plugin) {
|
||||||
Plugin floodgate = plugin.getProxy().getPluginManager().getPlugin("floodgate");
|
Plugin floodgate = plugin.getProxy().getPluginManager().getPlugin("floodgate");
|
||||||
Path geyserDataFolder = plugin.getDataFolder().toPath();
|
Path geyserDataFolder = plugin.getDataFolder().toPath();
|
||||||
|
|
|
@ -31,19 +31,25 @@ import net.md_5.bungee.api.config.ListenerInfo;
|
||||||
import net.md_5.bungee.api.plugin.Plugin;
|
import net.md_5.bungee.api.plugin.Plugin;
|
||||||
import net.md_5.bungee.protocol.ProtocolConstants;
|
import net.md_5.bungee.protocol.ProtocolConstants;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
import org.geysermc.common.PlatformType;
|
import org.geysermc.floodgate.BungeePlatform;
|
||||||
|
import org.geysermc.floodgate.pluginmessage.BungeeSkinApplier;
|
||||||
|
import org.geysermc.floodgate.skin.SkinApplier;
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.command.Command;
|
import org.geysermc.geyser.api.command.Command;
|
||||||
import org.geysermc.geyser.api.extension.Extension;
|
import org.geysermc.geyser.api.extension.Extension;
|
||||||
|
import org.geysermc.geyser.api.network.AuthType;
|
||||||
import org.geysermc.geyser.command.GeyserCommandManager;
|
import org.geysermc.geyser.command.GeyserCommandManager;
|
||||||
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
||||||
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
||||||
|
import org.geysermc.geyser.hybrid.HybridProvider;
|
||||||
|
import org.geysermc.geyser.hybrid.ProxyHybridProvider;
|
||||||
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
||||||
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
||||||
import org.geysermc.geyser.platform.bungeecord.command.GeyserBungeeCommandExecutor;
|
import org.geysermc.geyser.platform.bungeecord.command.GeyserBungeeCommandExecutor;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
@ -106,15 +112,29 @@ public class GeyserBungeePlugin extends Plugin implements GeyserBootstrap {
|
||||||
this.geyserLogger = new GeyserBungeeLogger(getLogger(), geyserConfig.isDebugMode());
|
this.geyserLogger = new GeyserBungeeLogger(getLogger(), geyserConfig.isDebugMode());
|
||||||
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
||||||
|
|
||||||
this.geyser = GeyserImpl.load(PlatformType.BUNGEECORD, this);
|
this.geyser = GeyserImpl.load(PlatformType.BUNGEECORD, this, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onEnable() {
|
public void onEnable() {
|
||||||
// Remove this in like a year
|
if (getProxy().getConfig().getListeners().size() == 1) {
|
||||||
if (getProxy().getPluginManager().getPlugin("floodgate-bungee") != null) {
|
ListenerInfo listener = getProxy().getConfig().getListeners().toArray(new ListenerInfo[0])[0];
|
||||||
geyserLogger.severe(GeyserLocale.getLocaleStringLog("geyser.bootstrap.floodgate.outdated", "https://ci.opencollab.dev/job/GeyserMC/job/Floodgate/job/master/"));
|
|
||||||
return;
|
InetSocketAddress javaAddr = listener.getHost();
|
||||||
|
|
||||||
|
// By default this should be localhost but may need to be changed in some circumstances
|
||||||
|
if (this.geyserConfig.getRemote().address().equalsIgnoreCase("auto")) {
|
||||||
|
this.geyserConfig.setAutoconfiguredRemote(true);
|
||||||
|
// Don't use localhost if not listening on all interfaces
|
||||||
|
if (!javaAddr.getHostString().equals("0.0.0.0") && !javaAddr.getHostString().equals("")) {
|
||||||
|
this.geyserConfig.getRemote().setAddress(javaAddr.getHostString());
|
||||||
|
}
|
||||||
|
this.geyserConfig.getRemote().setPort(javaAddr.getPort());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (geyserConfig.getBedrock().isCloneRemotePort()) {
|
||||||
|
geyserConfig.getBedrock().setPort(javaAddr.getPort());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Force-disable query if enabled, or else Geyser won't enable
|
// Force-disable query if enabled, or else Geyser won't enable
|
||||||
|
@ -135,6 +155,14 @@ public class GeyserBungeePlugin extends Plugin implements GeyserBootstrap {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (getProxy().getPluginManager().getPlugin("floodgate") != null) {
|
||||||
|
geyserLogger.warning("WHY DO YOU HAVE FLOODGATE INSTALLED???1/");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (geyserConfig.getRemote().authType() == AuthType.FLOODGATE) {
|
||||||
|
getProxy().getPluginManager().registerListener(this, new BungeeHybridListener());
|
||||||
|
}
|
||||||
|
|
||||||
// Big hack - Bungee does not provide us an event to listen to, so schedule a repeating
|
// Big hack - Bungee does not provide us an event to listen to, so schedule a repeating
|
||||||
// task that waits for a field to be filled which is set after the plugin enable
|
// task that waits for a field to be filled which is set after the plugin enable
|
||||||
// process is complete
|
// process is complete
|
||||||
|
@ -271,4 +299,15 @@ public class GeyserBungeePlugin extends Plugin implements GeyserBootstrap {
|
||||||
.map(info -> (InetSocketAddress) info.getSocketAddress())
|
.map(info -> (InetSocketAddress) info.getSocketAddress())
|
||||||
.findFirst();
|
.findFirst();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public HybridProvider createHybridProvider(GeyserImpl geyser) {
|
||||||
|
return new ProxyHybridProvider(geyser);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SkinApplier createSkinApplier() {
|
||||||
|
new BungeePlatform(this); // TODO hack to ensure ReflectionUtils prefix is applied and I don't forget about dealing with it
|
||||||
|
return new BungeeSkinApplier(null); // Also TODO
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -36,7 +36,6 @@ import net.minecraft.commands.CommandSourceStack;
|
||||||
import net.minecraft.commands.Commands;
|
import net.minecraft.commands.Commands;
|
||||||
import net.minecraft.server.MinecraftServer;
|
import net.minecraft.server.MinecraftServer;
|
||||||
import org.apache.logging.log4j.LogManager;
|
import org.apache.logging.log4j.LogManager;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.GeyserLogger;
|
import org.geysermc.geyser.GeyserLogger;
|
||||||
|
@ -52,6 +51,7 @@ import org.geysermc.geyser.platform.fabric.command.GeyserFabricCommandExecutor;
|
||||||
import org.geysermc.geyser.platform.fabric.world.GeyserFabricWorldManager;
|
import org.geysermc.geyser.platform.fabric.world.GeyserFabricWorldManager;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
|
|
|
@ -21,6 +21,8 @@ dependencies {
|
||||||
attribute(TargetJvmVersion.TARGET_JVM_VERSION_ATTRIBUTE, 17)
|
attribute(TargetJvmVersion.TARGET_JVM_VERSION_ATTRIBUTE, 17)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
implementation("org.geysermc.floodgate", "spigot", "2.2.0-SNAPSHOT")
|
||||||
}
|
}
|
||||||
|
|
||||||
platformRelocate("it.unimi.dsi.fastutil")
|
platformRelocate("it.unimi.dsi.fastutil")
|
||||||
|
@ -32,6 +34,7 @@ platformRelocate("me.lucko.commodore")
|
||||||
|
|
||||||
// These dependencies are already present on the platform
|
// These dependencies are already present on the platform
|
||||||
provided(libs.viaversion)
|
provided(libs.viaversion)
|
||||||
|
provided("com.mojang", "authlib", "1.5.21")
|
||||||
|
|
||||||
application {
|
application {
|
||||||
mainClass.set("org.geysermc.geyser.platform.spigot.GeyserSpigotMain")
|
mainClass.set("org.geysermc.geyser.platform.spigot.GeyserSpigotMain")
|
||||||
|
|
|
@ -41,6 +41,7 @@ public final class GeyserSpigotConfiguration extends GeyserJacksonConfiguration
|
||||||
@JsonIgnore
|
@JsonIgnore
|
||||||
private Path floodgateKeyPath;
|
private Path floodgateKeyPath;
|
||||||
|
|
||||||
|
// TODO REMOVE
|
||||||
public void loadFloodgate(GeyserSpigotPlugin plugin) {
|
public void loadFloodgate(GeyserSpigotPlugin plugin) {
|
||||||
Plugin floodgate = Bukkit.getPluginManager().getPlugin("floodgate");
|
Plugin floodgate = Bukkit.getPluginManager().getPlugin("floodgate");
|
||||||
Path geyserDataFolder = plugin.getDataFolder().toPath();
|
Path geyserDataFolder = plugin.getDataFolder().toPath();
|
||||||
|
|
|
@ -33,6 +33,8 @@ import io.netty.channel.local.LocalAddress;
|
||||||
import io.netty.util.concurrent.DefaultThreadFactory;
|
import io.netty.util.concurrent.DefaultThreadFactory;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.api.network.AuthType;
|
||||||
import org.geysermc.geyser.network.netty.GeyserInjector;
|
import org.geysermc.geyser.network.netty.GeyserInjector;
|
||||||
import org.geysermc.geyser.network.netty.LocalServerChannelWrapper;
|
import org.geysermc.geyser.network.netty.LocalServerChannelWrapper;
|
||||||
import org.geysermc.geyser.network.netty.LocalSession;
|
import org.geysermc.geyser.network.netty.LocalSession;
|
||||||
|
@ -119,10 +121,17 @@ public class GeyserSpigotInjector extends GeyserInjector {
|
||||||
@Override
|
@Override
|
||||||
protected void initChannel(Channel ch) throws Exception {
|
protected void initChannel(Channel ch) throws Exception {
|
||||||
initChannel.invoke(childHandler, ch);
|
initChannel.invoke(childHandler, ch);
|
||||||
|
|
||||||
if (bootstrap.getGeyserConfig().isDisableCompression() && GeyserSpigotCompressionDisabler.ENABLED) {
|
if (bootstrap.getGeyserConfig().isDisableCompression() && GeyserSpigotCompressionDisabler.ENABLED) {
|
||||||
ch.pipeline().addAfter("encoder", "geyser-compression-disabler", new GeyserSpigotCompressionDisabler());
|
ch.pipeline().addAfter("encoder", "geyser-compression-disabler", new GeyserSpigotCompressionDisabler());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (GeyserImpl.getInstance().getConfig().getRemote().authType() == AuthType.FLOODGATE) {
|
||||||
|
// we have to add the packet blocker in the data handler, otherwise ProtocolSupport breaks
|
||||||
|
ch.pipeline().addBefore(
|
||||||
|
"packet_handler", "geyser_data_handler",
|
||||||
|
new SpigotHybridChannelHandler()
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
// Set to MAX_PRIORITY as MultithreadEventLoopGroup#newDefaultThreadFactory which DefaultEventLoopGroup implements does by default
|
// Set to MAX_PRIORITY as MultithreadEventLoopGroup#newDefaultThreadFactory which DefaultEventLoopGroup implements does by default
|
||||||
|
@ -174,7 +183,7 @@ public class GeyserSpigotInjector extends GeyserInjector {
|
||||||
*/
|
*/
|
||||||
private void workAroundWeirdBug(GeyserBootstrap bootstrap) {
|
private void workAroundWeirdBug(GeyserBootstrap bootstrap) {
|
||||||
MinecraftProtocol protocol = new MinecraftProtocol();
|
MinecraftProtocol protocol = new MinecraftProtocol();
|
||||||
LocalSession session = new LocalSession(bootstrap.getGeyserConfig().getRemote().address(),
|
LocalSession session = new LocalSession(null, bootstrap.getGeyserConfig().getRemote().address(),
|
||||||
bootstrap.getGeyserConfig().getRemote().port(), this.serverSocketAddress,
|
bootstrap.getGeyserConfig().getRemote().port(), this.serverSocketAddress,
|
||||||
InetAddress.getLoopbackAddress().getHostAddress(), protocol, protocol.createHelper());
|
InetAddress.getLoopbackAddress().getHostAddress(), protocol, protocol.createHelper());
|
||||||
session.connect();
|
session.connect();
|
||||||
|
|
|
@ -42,7 +42,9 @@ import org.bukkit.permissions.Permission;
|
||||||
import org.bukkit.permissions.PermissionDefault;
|
import org.bukkit.permissions.PermissionDefault;
|
||||||
import org.bukkit.plugin.Plugin;
|
import org.bukkit.plugin.Plugin;
|
||||||
import org.bukkit.plugin.java.JavaPlugin;
|
import org.bukkit.plugin.java.JavaPlugin;
|
||||||
import org.geysermc.common.PlatformType;
|
import org.geysermc.floodgate.pluginmessage.SpigotSkinApplier;
|
||||||
|
import org.geysermc.floodgate.skin.SkinApplier;
|
||||||
|
import org.geysermc.floodgate.util.SpigotVersionSpecificMethods;
|
||||||
import org.geysermc.geyser.Constants;
|
import org.geysermc.geyser.Constants;
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
@ -52,6 +54,8 @@ import org.geysermc.geyser.api.extension.Extension;
|
||||||
import org.geysermc.geyser.command.GeyserCommandManager;
|
import org.geysermc.geyser.command.GeyserCommandManager;
|
||||||
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
||||||
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
||||||
|
import org.geysermc.geyser.hybrid.HybridProvider;
|
||||||
|
import org.geysermc.geyser.hybrid.IntegratedHybridProvider;
|
||||||
import org.geysermc.geyser.level.WorldManager;
|
import org.geysermc.geyser.level.WorldManager;
|
||||||
import org.geysermc.geyser.network.GameProtocol;
|
import org.geysermc.geyser.network.GameProtocol;
|
||||||
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
||||||
|
@ -66,6 +70,7 @@ import org.geysermc.geyser.platform.spigot.world.manager.GeyserSpigotNativeWorld
|
||||||
import org.geysermc.geyser.platform.spigot.world.manager.GeyserSpigotWorldManager;
|
import org.geysermc.geyser.platform.spigot.world.manager.GeyserSpigotWorldManager;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
@ -154,7 +159,7 @@ public class GeyserSpigotPlugin extends JavaPlugin implements GeyserBootstrap {
|
||||||
|
|
||||||
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
||||||
|
|
||||||
this.geyser = GeyserImpl.load(PlatformType.SPIGOT, this);
|
this.geyser = GeyserImpl.load(PlatformType.SPIGOT, this, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -165,11 +170,22 @@ public class GeyserSpigotPlugin extends JavaPlugin implements GeyserBootstrap {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Remove this in like a year
|
// By default this should be localhost but may need to be changed in some circumstances
|
||||||
if (Bukkit.getPluginManager().getPlugin("floodgate-bukkit") != null) {
|
if (this.geyserConfig.getRemote().address().equalsIgnoreCase("auto")) {
|
||||||
geyserLogger.severe(GeyserLocale.getLocaleStringLog("geyser.bootstrap.floodgate.outdated", Constants.FLOODGATE_DOWNLOAD_LOCATION));
|
geyserConfig.setAutoconfiguredRemote(true);
|
||||||
this.getPluginLoader().disablePlugin(this);
|
// Don't use localhost if not listening on all interfaces
|
||||||
return;
|
if (!Bukkit.getIp().equals("0.0.0.0") && !Bukkit.getIp().equals("")) {
|
||||||
|
geyserConfig.getRemote().setAddress(Bukkit.getIp());
|
||||||
|
}
|
||||||
|
geyserConfig.getRemote().setPort(Bukkit.getPort());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (geyserConfig.getBedrock().isCloneRemotePort()) {
|
||||||
|
geyserConfig.getBedrock().setPort(Bukkit.getPort());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Bukkit.getPluginManager().getPlugin("floodgate") != null) {
|
||||||
|
geyserLogger.severe("WHY DO YOU HAVE FLOODGATE INSTALLED!!!!!!! REMOVE IT!!!!");
|
||||||
}
|
}
|
||||||
|
|
||||||
this.geyserCommandManager = new GeyserSpigotCommandManager(geyser);
|
this.geyserCommandManager = new GeyserSpigotCommandManager(geyser);
|
||||||
|
@ -408,6 +424,16 @@ public class GeyserSpigotPlugin extends JavaPlugin implements GeyserBootstrap {
|
||||||
return this.geyserInjector.getServerSocketAddress();
|
return this.geyserInjector.getServerSocketAddress();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public HybridProvider createHybridProvider(GeyserImpl geyser) {
|
||||||
|
return new IntegratedHybridProvider(geyser);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SkinApplier createSkinApplier() {
|
||||||
|
return new SpigotSkinApplier(new SpigotVersionSpecificMethods(this), this);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return the server version before ViaVersion finishes initializing
|
* @return the server version before ViaVersion finishes initializing
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -0,0 +1,88 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2019-2022 GeyserMC. http://geysermc.org
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* @author GeyserMC
|
||||||
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.geysermc.geyser.platform.spigot;
|
||||||
|
|
||||||
|
import com.mojang.authlib.GameProfile;
|
||||||
|
import io.netty.channel.ChannelHandler;
|
||||||
|
import io.netty.channel.ChannelHandlerContext;
|
||||||
|
import io.netty.channel.ChannelInboundHandlerAdapter;
|
||||||
|
import org.geysermc.floodgate.util.ClassNames;
|
||||||
|
import org.geysermc.geyser.hybrid.IntegratedHybridProvider;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
|
import javax.annotation.Nonnull;
|
||||||
|
|
||||||
|
import static org.geysermc.floodgate.util.ReflectionUtils.setValue;
|
||||||
|
|
||||||
|
@ChannelHandler.Sharable
|
||||||
|
public final class SpigotHybridChannelHandler extends ChannelInboundHandlerAdapter {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void channelRead(@Nonnull ChannelHandlerContext ctx, @Nonnull Object packet) throws Exception {
|
||||||
|
GeyserSession session = ctx.channel().attr(IntegratedHybridProvider.SESSION_KEY).get();
|
||||||
|
// TODO generify this code within Floodgate
|
||||||
|
if (ClassNames.LOGIN_START_PACKET.isInstance(packet)) {
|
||||||
|
Object networkManager = ctx.channel().pipeline().get("packet_handler");
|
||||||
|
Object packetListener = ClassNames.PACKET_LISTENER.get(networkManager);
|
||||||
|
|
||||||
|
setValue(networkManager, "spoofedUUID", session.javaUuid());
|
||||||
|
|
||||||
|
// check if the server is actually in the Login state
|
||||||
|
if (!ClassNames.LOGIN_LISTENER.isInstance(packetListener)) {
|
||||||
|
// player is not in the login state, abort
|
||||||
|
|
||||||
|
// I would've liked to close the channel for security reasons, but our big friend
|
||||||
|
// ProtocolSupport, who likes to break things, doesn't work otherwise
|
||||||
|
ctx.pipeline().remove(this);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// set the player his GameProfile, we can't change the username without this
|
||||||
|
GameProfile gameProfile = new GameProfile(
|
||||||
|
// TODO testing only
|
||||||
|
session.javaUuid(), session.javaUsername()
|
||||||
|
);
|
||||||
|
setValue(packetListener, ClassNames.LOGIN_PROFILE, gameProfile);
|
||||||
|
|
||||||
|
// we have to fake the offline player (login) cycle
|
||||||
|
// just like on Spigot:
|
||||||
|
|
||||||
|
// LoginListener#initUUID
|
||||||
|
// new LoginHandler().fireEvents();
|
||||||
|
|
||||||
|
// and the tick of LoginListener will do the rest
|
||||||
|
|
||||||
|
ClassNames.INIT_UUID.invoke(packetListener);
|
||||||
|
|
||||||
|
Object loginHandler = ClassNames.LOGIN_HANDLER_CONSTRUCTOR.newInstance(packetListener);
|
||||||
|
ClassNames.FIRE_LOGIN_EVENTS.invoke(loginHandler);
|
||||||
|
|
||||||
|
ctx.pipeline().remove(this);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
ctx.fireChannelRead(packet);
|
||||||
|
}
|
||||||
|
}
|
|
@ -27,7 +27,6 @@ package org.geysermc.geyser.platform.sponge;
|
||||||
|
|
||||||
import com.google.inject.Inject;
|
import com.google.inject.Inject;
|
||||||
import org.apache.logging.log4j.Logger;
|
import org.apache.logging.log4j.Logger;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.command.Command;
|
import org.geysermc.geyser.api.command.Command;
|
||||||
|
@ -37,10 +36,11 @@ import org.geysermc.geyser.configuration.GeyserConfiguration;
|
||||||
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
||||||
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
||||||
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
||||||
import org.geysermc.geyser.platform.sponge.command.GeyserSpongeCommandManager;
|
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
|
||||||
import org.geysermc.geyser.platform.sponge.command.GeyserSpongeCommandExecutor;
|
import org.geysermc.geyser.platform.sponge.command.GeyserSpongeCommandExecutor;
|
||||||
|
import org.geysermc.geyser.platform.sponge.command.GeyserSpongeCommandManager;
|
||||||
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.spongepowered.api.Server;
|
import org.spongepowered.api.Server;
|
||||||
import org.spongepowered.api.Sponge;
|
import org.spongepowered.api.Sponge;
|
||||||
|
@ -142,7 +142,7 @@ public class GeyserSpongePlugin implements GeyserBootstrap {
|
||||||
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
||||||
this.geyserLogger = new GeyserSpongeLogger(logger, geyserConfig.isDebugMode());
|
this.geyserLogger = new GeyserSpongeLogger(logger, geyserConfig.isDebugMode());
|
||||||
|
|
||||||
this.geyser = GeyserImpl.load(PlatformType.SPONGE, this);
|
this.geyser = GeyserImpl.load(PlatformType.SPONGE, this, null);
|
||||||
|
|
||||||
this.geyserCommandManager = new GeyserSpongeCommandManager(geyser);
|
this.geyserCommandManager = new GeyserSpongeCommandManager(geyser);
|
||||||
this.geyserCommandManager.init();
|
this.geyserCommandManager.init();
|
||||||
|
|
|
@ -38,7 +38,6 @@ import org.apache.logging.log4j.LogManager;
|
||||||
import org.apache.logging.log4j.core.Appender;
|
import org.apache.logging.log4j.core.Appender;
|
||||||
import org.apache.logging.log4j.core.Logger;
|
import org.apache.logging.log4j.core.Logger;
|
||||||
import org.apache.logging.log4j.core.appender.ConsoleAppender;
|
import org.apache.logging.log4j.core.appender.ConsoleAppender;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommandManager;
|
import org.geysermc.geyser.command.GeyserCommandManager;
|
||||||
|
@ -51,6 +50,7 @@ import org.geysermc.geyser.platform.standalone.gui.GeyserStandaloneGUI;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
import org.geysermc.geyser.util.LoopbackUtil;
|
import org.geysermc.geyser.util.LoopbackUtil;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
@ -217,7 +217,7 @@ public class GeyserStandaloneBootstrap implements GeyserBootstrap {
|
||||||
// Allow libraries like Protocol to have their debug information passthrough
|
// Allow libraries like Protocol to have their debug information passthrough
|
||||||
logger.get().setLevel(geyserConfig.isDebugMode() ? Level.DEBUG : Level.INFO);
|
logger.get().setLevel(geyserConfig.isDebugMode() ? Level.DEBUG : Level.INFO);
|
||||||
|
|
||||||
geyser = GeyserImpl.load(PlatformType.STANDALONE, this);
|
geyser = GeyserImpl.load(PlatformType.STANDALONE, this, null);
|
||||||
GeyserImpl.start();
|
GeyserImpl.start();
|
||||||
|
|
||||||
geyserCommandManager = new GeyserCommandManager(geyser);
|
geyserCommandManager = new GeyserCommandManager(geyser);
|
||||||
|
|
|
@ -310,7 +310,7 @@ public class GeyserStandaloneGUI {
|
||||||
|
|
||||||
for (GeyserSession player : GeyserImpl.getInstance().getSessionManager().getSessions().values()) {
|
for (GeyserSession player : GeyserImpl.getInstance().getSessionManager().getSessions().values()) {
|
||||||
Vector<String> row = new Vector<>();
|
Vector<String> row = new Vector<>();
|
||||||
row.add(player.getSocketAddress().getHostName());
|
row.add(player.socketAddress().getHostName());
|
||||||
row.add(player.getPlayerEntity().getUsername());
|
row.add(player.getPlayerEntity().getUsername());
|
||||||
|
|
||||||
playerTableModel.addRow(row);
|
playerTableModel.addRow(row);
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
dependencies {
|
dependencies {
|
||||||
annotationProcessor(libs.velocity.api)
|
annotationProcessor(libs.velocity.api)
|
||||||
|
implementation("org.geysermc.floodgate", "velocity", "2.2.0-SNAPSHOT")
|
||||||
api(projects.core)
|
api(projects.core)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -26,6 +26,7 @@
|
||||||
package org.geysermc.geyser.platform.velocity;
|
package org.geysermc.geyser.platform.velocity;
|
||||||
|
|
||||||
import com.google.inject.Inject;
|
import com.google.inject.Inject;
|
||||||
|
import com.google.inject.Injector;
|
||||||
import com.velocitypowered.api.command.CommandManager;
|
import com.velocitypowered.api.command.CommandManager;
|
||||||
import com.velocitypowered.api.event.Subscribe;
|
import com.velocitypowered.api.event.Subscribe;
|
||||||
import com.velocitypowered.api.event.proxy.ListenerBoundEvent;
|
import com.velocitypowered.api.event.proxy.ListenerBoundEvent;
|
||||||
|
@ -36,19 +37,22 @@ import com.velocitypowered.api.plugin.Plugin;
|
||||||
import com.velocitypowered.api.proxy.ProxyServer;
|
import com.velocitypowered.api.proxy.ProxyServer;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import net.kyori.adventure.util.Codec;
|
import net.kyori.adventure.util.Codec;
|
||||||
import org.geysermc.common.PlatformType;
|
import org.geysermc.floodgate.FloodgatePlatform;
|
||||||
import org.geysermc.geyser.GeyserBootstrap;
|
import org.geysermc.geyser.GeyserBootstrap;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.command.Command;
|
import org.geysermc.geyser.api.command.Command;
|
||||||
import org.geysermc.geyser.api.extension.Extension;
|
import org.geysermc.geyser.api.extension.Extension;
|
||||||
|
import org.geysermc.geyser.api.network.AuthType;
|
||||||
import org.geysermc.geyser.command.GeyserCommandManager;
|
import org.geysermc.geyser.command.GeyserCommandManager;
|
||||||
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
||||||
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
||||||
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
import org.geysermc.geyser.ping.GeyserLegacyPingPassthrough;
|
||||||
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
||||||
import org.geysermc.geyser.platform.velocity.command.GeyserVelocityCommandExecutor;
|
import org.geysermc.geyser.platform.velocity.command.GeyserVelocityCommandExecutor;
|
||||||
|
import org.geysermc.geyser.platform.velocity.floodgate.FloodgateVelocityPlatform;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.FileUtils;
|
import org.geysermc.geyser.util.FileUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
|
@ -84,6 +88,9 @@ public class GeyserVelocityPlugin implements GeyserBootstrap {
|
||||||
@Getter
|
@Getter
|
||||||
private final Path configFolder = Paths.get("plugins/" + GeyserImpl.NAME + "-Velocity/");
|
private final Path configFolder = Paths.get("plugins/" + GeyserImpl.NAME + "-Velocity/");
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private Injector guice;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onEnable() {
|
public void onEnable() {
|
||||||
try {
|
try {
|
||||||
|
@ -113,7 +120,12 @@ public class GeyserVelocityPlugin implements GeyserBootstrap {
|
||||||
this.geyserLogger = new GeyserVelocityLogger(logger, geyserConfig.isDebugMode());
|
this.geyserLogger = new GeyserVelocityLogger(logger, geyserConfig.isDebugMode());
|
||||||
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
GeyserConfiguration.checkGeyserConfiguration(geyserConfig, geyserLogger);
|
||||||
|
|
||||||
this.geyser = GeyserImpl.load(PlatformType.VELOCITY, this);
|
FloodgatePlatform platform = null;
|
||||||
|
if (geyserConfig.getRemote().authType() == AuthType.FLOODGATE) {
|
||||||
|
platform = guice.getInstance(FloodgateVelocityPlatform.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
this.geyser = GeyserImpl.load(PlatformType.VELOCITY, this, platform);
|
||||||
|
|
||||||
// Remove this in like a year
|
// Remove this in like a year
|
||||||
try {
|
try {
|
||||||
|
@ -124,6 +136,19 @@ public class GeyserVelocityPlugin implements GeyserBootstrap {
|
||||||
return;
|
return;
|
||||||
} catch (ClassNotFoundException ignored) {
|
} catch (ClassNotFoundException ignored) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// if (geyserConfig.getRemote().authType() == AuthType.FLOODGATE && proxyServer.getPluginManager().getPlugin("floodgate").isEmpty()) {
|
||||||
|
// geyserLogger.severe(GeyserLocale.getLocaleStringLog("geyser.bootstrap.floodgate.not_installed") + " "
|
||||||
|
// + GeyserLocale.getLocaleStringLog("geyser.bootstrap.floodgate.disabling"));
|
||||||
|
// return;
|
||||||
|
// } else if (geyserConfig.isAutoconfiguredRemote() && proxyServer.getPluginManager().getPlugin("floodgate").isPresent()) {
|
||||||
|
// // Floodgate installed means that the user wants Floodgate authentication
|
||||||
|
// geyserLogger.debug("Auto-setting to Floodgate authentication.");
|
||||||
|
// geyserConfig.getRemote().setAuthType(AuthType.FLOODGATE);
|
||||||
|
// }
|
||||||
|
|
||||||
|
geyserConfig.loadFloodgate(this, proxyServer, configFolder.toFile());
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void postStartup() {
|
private void postStartup() {
|
||||||
|
|
|
@ -0,0 +1,46 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2019-2022 GeyserMC. http://geysermc.org
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* @author GeyserMC
|
||||||
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.geysermc.geyser.platform.velocity.floodgate;
|
||||||
|
|
||||||
|
import com.google.inject.Module;
|
||||||
|
import org.geysermc.floodgate.VelocityPlatform;
|
||||||
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.floodgate.GeyserLoadStage;
|
||||||
|
|
||||||
|
import java.nio.file.Paths;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
public class FloodgateVelocityPlatform extends VelocityPlatform {
|
||||||
|
@Override
|
||||||
|
protected List<Module> loadStageModules() {
|
||||||
|
// Geyser being a dumb dumb
|
||||||
|
super.dataDirectory = Paths.get("plugins/" + GeyserImpl.NAME + "-Velocity/");
|
||||||
|
|
||||||
|
var loaded = super.loadStageModules();
|
||||||
|
loaded.add(new GeyserLoadStage());
|
||||||
|
return loaded;
|
||||||
|
}
|
||||||
|
}
|
|
@ -6,7 +6,7 @@ plugins {
|
||||||
|
|
||||||
allprojects {
|
allprojects {
|
||||||
group = "org.geysermc.geyser"
|
group = "org.geysermc.geyser"
|
||||||
version = "2.1.0-SNAPSHOT"
|
version = "3.0.0-SNAPSHOT"
|
||||||
description = "Allows for players from Minecraft: Bedrock Edition to join Minecraft: Java Edition servers."
|
description = "Allows for players from Minecraft: Bedrock Edition to join Minecraft: Java Edition servers."
|
||||||
|
|
||||||
tasks.withType<JavaCompile> {
|
tasks.withType<JavaCompile> {
|
||||||
|
|
|
@ -7,7 +7,7 @@ plugins {
|
||||||
}
|
}
|
||||||
|
|
||||||
dependencies {
|
dependencies {
|
||||||
api(projects.common)
|
api("org.geysermc.floodgate", "core", "2.2.0-SNAPSHOT")
|
||||||
api(projects.api)
|
api(projects.api)
|
||||||
|
|
||||||
// Jackson JSON and YAML serialization
|
// Jackson JSON and YAML serialization
|
||||||
|
|
|
@ -26,9 +26,9 @@
|
||||||
package org.geysermc.connector;
|
package org.geysermc.connector;
|
||||||
|
|
||||||
import org.geysermc.api.Geyser;
|
import org.geysermc.api.Geyser;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.connector.network.session.GeyserSession;
|
import org.geysermc.connector.network.session.GeyserSession;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
|
|
@ -25,9 +25,12 @@
|
||||||
|
|
||||||
package org.geysermc.geyser;
|
package org.geysermc.geyser;
|
||||||
|
|
||||||
|
import org.geysermc.floodgate.skin.SkinApplier;
|
||||||
import org.geysermc.geyser.command.GeyserCommandManager;
|
import org.geysermc.geyser.command.GeyserCommandManager;
|
||||||
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
import org.geysermc.geyser.configuration.GeyserConfiguration;
|
||||||
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
import org.geysermc.geyser.dump.BootstrapDumpInfo;
|
||||||
|
import org.geysermc.geyser.hybrid.FloodgateHybridProvider;
|
||||||
|
import org.geysermc.geyser.hybrid.HybridProvider;
|
||||||
import org.geysermc.geyser.level.GeyserWorldManager;
|
import org.geysermc.geyser.level.GeyserWorldManager;
|
||||||
import org.geysermc.geyser.level.WorldManager;
|
import org.geysermc.geyser.level.WorldManager;
|
||||||
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
import org.geysermc.geyser.ping.IGeyserPingPassthrough;
|
||||||
|
@ -134,6 +137,20 @@ public interface GeyserBootstrap {
|
||||||
return Paths.get("logs/latest.log");
|
return Paths.get("logs/latest.log");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates the hybrid provider for this platform. The provider will differ based on server access.
|
||||||
|
*/
|
||||||
|
default HybridProvider createHybridProvider(GeyserImpl geyser) {
|
||||||
|
return new FloodgateHybridProvider(geyser);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the skin applier for this platform, if the hybrid provider is integrated with the system.
|
||||||
|
*/
|
||||||
|
default SkinApplier createSkinApplier() {
|
||||||
|
throw new IllegalStateException();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get an InputStream for the given resource path.
|
* Get an InputStream for the given resource path.
|
||||||
* Overridden on platforms that have different class loader properties.
|
* Overridden on platforms that have different class loader properties.
|
||||||
|
|
|
@ -43,14 +43,10 @@ import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
|
||||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
import org.checkerframework.checker.nullness.qual.Nullable;
|
import org.checkerframework.checker.nullness.qual.Nullable;
|
||||||
import org.geysermc.api.Geyser;
|
import org.geysermc.api.Geyser;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.cumulus.form.Form;
|
import org.geysermc.cumulus.form.Form;
|
||||||
import org.geysermc.cumulus.form.util.FormBuilder;
|
import org.geysermc.cumulus.form.util.FormBuilder;
|
||||||
import org.geysermc.erosion.packet.Packets;
|
import org.geysermc.erosion.packet.Packets;
|
||||||
import org.geysermc.floodgate.crypto.AesCipher;
|
import org.geysermc.floodgate.FloodgatePlatform;
|
||||||
import org.geysermc.floodgate.crypto.AesKeyProducer;
|
|
||||||
import org.geysermc.floodgate.crypto.Base64Topping;
|
|
||||||
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
|
||||||
import org.geysermc.floodgate.news.NewsItemAction;
|
import org.geysermc.floodgate.news.NewsItemAction;
|
||||||
import org.geysermc.geyser.api.GeyserApi;
|
import org.geysermc.geyser.api.GeyserApi;
|
||||||
import org.geysermc.geyser.api.event.EventBus;
|
import org.geysermc.geyser.api.event.EventBus;
|
||||||
|
@ -67,6 +63,7 @@ import org.geysermc.geyser.entity.EntityDefinitions;
|
||||||
import org.geysermc.geyser.erosion.UnixSocketClientListener;
|
import org.geysermc.geyser.erosion.UnixSocketClientListener;
|
||||||
import org.geysermc.geyser.event.GeyserEventBus;
|
import org.geysermc.geyser.event.GeyserEventBus;
|
||||||
import org.geysermc.geyser.extension.GeyserExtensionManager;
|
import org.geysermc.geyser.extension.GeyserExtensionManager;
|
||||||
|
import org.geysermc.geyser.hybrid.HybridProvider;
|
||||||
import org.geysermc.geyser.level.WorldManager;
|
import org.geysermc.geyser.level.WorldManager;
|
||||||
import org.geysermc.geyser.network.netty.GeyserServer;
|
import org.geysermc.geyser.network.netty.GeyserServer;
|
||||||
import org.geysermc.geyser.pack.ResourcePack;
|
import org.geysermc.geyser.pack.ResourcePack;
|
||||||
|
@ -76,7 +73,7 @@ import org.geysermc.geyser.scoreboard.ScoreboardUpdater;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.session.PendingMicrosoftAuthentication;
|
import org.geysermc.geyser.session.PendingMicrosoftAuthentication;
|
||||||
import org.geysermc.geyser.session.SessionManager;
|
import org.geysermc.geyser.session.SessionManager;
|
||||||
import org.geysermc.geyser.skin.FloodgateSkinUploader;
|
import org.geysermc.geyser.skin.BedrockSkinUploader;
|
||||||
import org.geysermc.geyser.skin.ProvidedSkins;
|
import org.geysermc.geyser.skin.ProvidedSkins;
|
||||||
import org.geysermc.geyser.skin.SkinProvider;
|
import org.geysermc.geyser.skin.SkinProvider;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
@ -90,7 +87,6 @@ import java.io.IOException;
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
import java.net.InetSocketAddress;
|
import java.net.InetSocketAddress;
|
||||||
import java.net.UnknownHostException;
|
import java.net.UnknownHostException;
|
||||||
import java.security.Key;
|
|
||||||
import java.text.DecimalFormat;
|
import java.text.DecimalFormat;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
import java.util.concurrent.CompletableFuture;
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
@ -133,8 +129,8 @@ public class GeyserImpl implements GeyserApi {
|
||||||
@Setter
|
@Setter
|
||||||
private static boolean shouldStartListener = true;
|
private static boolean shouldStartListener = true;
|
||||||
|
|
||||||
private FloodgateCipher cipher;
|
private HybridProvider hybridProvider;
|
||||||
private FloodgateSkinUploader skinUploader;
|
private BedrockSkinUploader skinUploader;
|
||||||
private NewsHandler newsHandler;
|
private NewsHandler newsHandler;
|
||||||
|
|
||||||
private UnixSocketClientListener erosionUnixListener;
|
private UnixSocketClientListener erosionUnixListener;
|
||||||
|
@ -158,10 +154,18 @@ public class GeyserImpl implements GeyserApi {
|
||||||
|
|
||||||
private static GeyserImpl instance;
|
private static GeyserImpl instance;
|
||||||
|
|
||||||
private GeyserImpl(PlatformType platformType, GeyserBootstrap bootstrap) {
|
private final FloodgatePlatform floodgatePlatform;
|
||||||
instance = this;
|
|
||||||
|
|
||||||
Geyser.set(this);
|
private GeyserImpl(PlatformType platformType, GeyserBootstrap bootstrap, FloodgatePlatform floodgatePlatform) {
|
||||||
|
instance = this;
|
||||||
|
this.floodgatePlatform = floodgatePlatform;
|
||||||
|
|
||||||
|
if (floodgatePlatform != null) {
|
||||||
|
floodgatePlatform.load();
|
||||||
|
floodgatePlatform.enable();
|
||||||
|
} else {
|
||||||
|
Geyser.set(this);
|
||||||
|
}
|
||||||
|
|
||||||
this.platformType = platformType;
|
this.platformType = platformType;
|
||||||
this.bootstrap = bootstrap;
|
this.bootstrap = bootstrap;
|
||||||
|
@ -259,7 +263,7 @@ public class GeyserImpl implements GeyserApi {
|
||||||
SkinProvider.registerCacheImageTask(this);
|
SkinProvider.registerCacheImageTask(this);
|
||||||
|
|
||||||
ResourcePack.loadPacks();
|
ResourcePack.loadPacks();
|
||||||
|
//TODO start
|
||||||
String geyserUdpPort = System.getProperty("geyserUdpPort", "");
|
String geyserUdpPort = System.getProperty("geyserUdpPort", "");
|
||||||
String pluginUdpPort = geyserUdpPort.isEmpty() ? System.getProperty("pluginUdpPort", "") : geyserUdpPort;
|
String pluginUdpPort = geyserUdpPort.isEmpty() ? System.getProperty("pluginUdpPort", "") : geyserUdpPort;
|
||||||
if ("-1".equals(pluginUdpPort)) {
|
if ("-1".equals(pluginUdpPort)) {
|
||||||
|
@ -335,6 +339,7 @@ public class GeyserImpl implements GeyserApi {
|
||||||
config.getRemote().setAuthType(AuthType.FLOODGATE);
|
config.getRemote().setAuthType(AuthType.FLOODGATE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
//TODO end
|
||||||
|
|
||||||
String remoteAddress = config.getRemote().address();
|
String remoteAddress = config.getRemote().address();
|
||||||
// Filters whether it is not an IP address or localhost, because otherwise it is not possible to find out an SRV entry.
|
// Filters whether it is not an IP address or localhost, because otherwise it is not possible to find out an SRV entry.
|
||||||
|
@ -392,16 +397,14 @@ public class GeyserImpl implements GeyserApi {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (config.getRemote().authType() == AuthType.FLOODGATE) {
|
if (config.getRemote().authType() == AuthType.FLOODGATE) {
|
||||||
|
hybridProvider = bootstrap.createHybridProvider(this);
|
||||||
try {
|
try {
|
||||||
Key key = new AesKeyProducer().produceFrom(config.getFloodgateKeyPath());
|
|
||||||
cipher = new AesCipher(new Base64Topping());
|
|
||||||
cipher.init(key);
|
|
||||||
logger.debug("Loaded Floodgate key!");
|
|
||||||
// Note: this is positioned after the bind so the skin uploader doesn't try to run if Geyser fails
|
// Note: this is positioned after the bind so the skin uploader doesn't try to run if Geyser fails
|
||||||
// to load successfully. Spigot complains about class loader if the plugin is disabled.
|
// to load successfully. Spigot complains about class loader if the plugin is disabled.
|
||||||
skinUploader = new FloodgateSkinUploader(this).start();
|
// TODO not Floodgate exclusive?
|
||||||
|
skinUploader = new BedrockSkinUploader(this).start();
|
||||||
} catch (Exception exception) {
|
} catch (Exception exception) {
|
||||||
logger.severe(GeyserLocale.getLocaleStringLog("geyser.auth.floodgate.bad_key"), exception);
|
logger.severe("Could not start the skin uploader!", exception);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -687,9 +690,9 @@ public class GeyserImpl implements GeyserApi {
|
||||||
return Integer.parseInt(BUILD_NUMBER);
|
return Integer.parseInt(BUILD_NUMBER);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static GeyserImpl load(PlatformType platformType, GeyserBootstrap bootstrap) {
|
public static GeyserImpl load(PlatformType platformType, GeyserBootstrap bootstrap, FloodgatePlatform floodgatePlatform) {
|
||||||
if (instance == null) {
|
if (instance == null) {
|
||||||
return new GeyserImpl(platformType, bootstrap);
|
return new GeyserImpl(platformType, bootstrap, floodgatePlatform);
|
||||||
}
|
}
|
||||||
|
|
||||||
return instance;
|
return instance;
|
||||||
|
|
|
@ -29,38 +29,22 @@ import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.RequiredArgsConstructor;
|
import lombok.RequiredArgsConstructor;
|
||||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.command.Command;
|
import org.geysermc.geyser.api.command.Command;
|
||||||
import org.geysermc.geyser.api.command.CommandExecutor;
|
import org.geysermc.geyser.api.command.CommandExecutor;
|
||||||
import org.geysermc.geyser.api.command.CommandSource;
|
import org.geysermc.geyser.api.command.CommandSource;
|
||||||
import org.geysermc.geyser.api.event.lifecycle.GeyserDefineCommandsEvent;
|
import org.geysermc.geyser.api.event.lifecycle.GeyserDefineCommandsEvent;
|
||||||
import org.geysermc.geyser.api.extension.Extension;
|
import org.geysermc.geyser.api.extension.Extension;
|
||||||
import org.geysermc.geyser.command.defaults.AdvancedTooltipsCommand;
|
import org.geysermc.geyser.command.defaults.*;
|
||||||
import org.geysermc.geyser.command.defaults.AdvancementsCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.ConnectionTestCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.DumpCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.ExtensionsCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.HelpCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.ListCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.OffhandCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.ReloadCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.SettingsCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.StatisticsCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.StopCommand;
|
|
||||||
import org.geysermc.geyser.command.defaults.VersionCommand;
|
|
||||||
import org.geysermc.geyser.event.type.GeyserDefineCommandsEventImpl;
|
import org.geysermc.geyser.event.type.GeyserDefineCommandsEventImpl;
|
||||||
import org.geysermc.geyser.extension.command.GeyserExtensionCommand;
|
import org.geysermc.geyser.extension.command.GeyserExtensionCommand;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.*;
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Locale;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
@RequiredArgsConstructor
|
@RequiredArgsConstructor
|
||||||
public class GeyserCommandManager {
|
public class GeyserCommandManager {
|
||||||
|
|
|
@ -26,13 +26,13 @@
|
||||||
package org.geysermc.geyser.command.defaults;
|
package org.geysermc.geyser.command.defaults;
|
||||||
|
|
||||||
import com.fasterxml.jackson.databind.JsonNode;
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
import org.geysermc.geyser.command.GeyserCommandSource;
|
import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.util.LoopbackUtil;
|
import org.geysermc.geyser.util.LoopbackUtil;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.geysermc.geyser.util.WebUtils;
|
import org.geysermc.geyser.util.WebUtils;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
|
|
|
@ -30,7 +30,6 @@ import com.fasterxml.jackson.core.util.DefaultPrettyPrinter;
|
||||||
import com.fasterxml.jackson.databind.JsonNode;
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
import org.geysermc.geyser.command.GeyserCommandSource;
|
import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
|
@ -39,6 +38,7 @@ import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.AsteriskSerializer;
|
import org.geysermc.geyser.text.AsteriskSerializer;
|
||||||
import org.geysermc.geyser.text.ChatColor;
|
import org.geysermc.geyser.text.ChatColor;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.geysermc.geyser.util.WebUtils;
|
import org.geysermc.geyser.util.WebUtils;
|
||||||
|
|
||||||
import java.io.FileOutputStream;
|
import java.io.FileOutputStream;
|
||||||
|
|
|
@ -25,7 +25,6 @@
|
||||||
|
|
||||||
package org.geysermc.geyser.command.defaults;
|
package org.geysermc.geyser.command.defaults;
|
||||||
|
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.command.Command;
|
import org.geysermc.geyser.api.command.Command;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
|
@ -33,6 +32,7 @@ import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.ChatColor;
|
import org.geysermc.geyser.text.ChatColor;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
|
@ -25,12 +25,12 @@
|
||||||
|
|
||||||
package org.geysermc.geyser.command.defaults;
|
package org.geysermc.geyser.command.defaults;
|
||||||
|
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
import org.geysermc.geyser.command.GeyserCommandSource;
|
import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
public class ReloadCommand extends GeyserCommand {
|
public class ReloadCommand extends GeyserCommand {
|
||||||
|
|
||||||
|
|
|
@ -25,12 +25,12 @@
|
||||||
|
|
||||||
package org.geysermc.geyser.command.defaults;
|
package org.geysermc.geyser.command.defaults;
|
||||||
|
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
import org.geysermc.geyser.command.GeyserCommandSource;
|
import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
|
|
|
@ -26,7 +26,6 @@
|
||||||
package org.geysermc.geyser.command.defaults;
|
package org.geysermc.geyser.command.defaults;
|
||||||
|
|
||||||
import org.cloudburstmc.protocol.bedrock.codec.BedrockCodec;
|
import org.cloudburstmc.protocol.bedrock.codec.BedrockCodec;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.command.GeyserCommand;
|
import org.geysermc.geyser.command.GeyserCommand;
|
||||||
import org.geysermc.geyser.command.GeyserCommandSource;
|
import org.geysermc.geyser.command.GeyserCommandSource;
|
||||||
|
@ -34,6 +33,7 @@ import org.geysermc.geyser.network.GameProtocol;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.ChatColor;
|
import org.geysermc.geyser.text.ChatColor;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
import org.geysermc.geyser.util.WebUtils;
|
import org.geysermc.geyser.util.WebUtils;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -51,6 +51,8 @@ public interface GeyserConfiguration {
|
||||||
|
|
||||||
IRemoteConfiguration getRemote();
|
IRemoteConfiguration getRemote();
|
||||||
|
|
||||||
|
HybridInfo getHybridInfo();
|
||||||
|
|
||||||
List<String> getSavedUserLogins();
|
List<String> getSavedUserLogins();
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
@ -164,6 +166,13 @@ public interface GeyserConfiguration {
|
||||||
void setAuthType(AuthType authType);
|
void setAuthType(AuthType authType);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO this is definitely temporary
|
||||||
|
interface HybridInfo {
|
||||||
|
String usernamePrefix();
|
||||||
|
|
||||||
|
boolean replaceSpaces();
|
||||||
|
}
|
||||||
|
|
||||||
interface IUserAuthenticationInfo {
|
interface IUserAuthenticationInfo {
|
||||||
String getEmail();
|
String getEmail();
|
||||||
|
|
||||||
|
|
|
@ -59,6 +59,18 @@ public abstract class GeyserJacksonConfiguration implements GeyserConfiguration
|
||||||
private BedrockConfiguration bedrock = new BedrockConfiguration();
|
private BedrockConfiguration bedrock = new BedrockConfiguration();
|
||||||
private RemoteConfiguration remote = new RemoteConfiguration();
|
private RemoteConfiguration remote = new RemoteConfiguration();
|
||||||
|
|
||||||
|
private HybridInfo hybridInfo = new HybridInfo() {
|
||||||
|
@Override
|
||||||
|
public String usernamePrefix() {
|
||||||
|
return ".";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean replaceSpaces() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
@JsonProperty("saved-user-logins")
|
@JsonProperty("saved-user-logins")
|
||||||
private List<String> savedUserLogins = Collections.emptyList();
|
private List<String> savedUserLogins = Collections.emptyList();
|
||||||
|
|
||||||
|
|
|
@ -27,9 +27,9 @@ package org.geysermc.geyser.dump;
|
||||||
|
|
||||||
import lombok.AllArgsConstructor;
|
import lombok.AllArgsConstructor;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.text.AsteriskSerializer;
|
import org.geysermc.geyser.text.AsteriskSerializer;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
|
@ -36,8 +36,7 @@ import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
|
||||||
import lombok.AllArgsConstructor;
|
import lombok.AllArgsConstructor;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import org.cloudburstmc.protocol.bedrock.codec.BedrockCodec;
|
import org.cloudburstmc.protocol.bedrock.codec.BedrockCodec;
|
||||||
import org.geysermc.floodgate.util.DeviceOs;
|
import org.geysermc.api.util.BedrockPlatform;
|
||||||
import org.geysermc.floodgate.util.FloodgateInfoHolder;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.api.GeyserApi;
|
import org.geysermc.geyser.api.GeyserApi;
|
||||||
import org.geysermc.geyser.api.extension.Extension;
|
import org.geysermc.geyser.api.extension.Extension;
|
||||||
|
@ -78,7 +77,7 @@ public class DumpInfo {
|
||||||
private final GitInfo gitInfo;
|
private final GitInfo gitInfo;
|
||||||
private final GeyserConfiguration config;
|
private final GeyserConfiguration config;
|
||||||
private final Floodgate floodgate;
|
private final Floodgate floodgate;
|
||||||
private final Object2IntMap<DeviceOs> userPlatforms;
|
private final Object2IntMap<BedrockPlatform> userPlatforms;
|
||||||
private final HashInfo hashInfo;
|
private final HashInfo hashInfo;
|
||||||
private final RamInfo ramInfo;
|
private final RamInfo ramInfo;
|
||||||
private LogsInfo logsInfo;
|
private LogsInfo logsInfo;
|
||||||
|
@ -126,7 +125,7 @@ public class DumpInfo {
|
||||||
|
|
||||||
this.userPlatforms = new Object2IntOpenHashMap<>();
|
this.userPlatforms = new Object2IntOpenHashMap<>();
|
||||||
for (GeyserSession session : GeyserImpl.getInstance().getSessionManager().getAllSessions()) {
|
for (GeyserSession session : GeyserImpl.getInstance().getSessionManager().getAllSessions()) {
|
||||||
DeviceOs device = session.getClientData().getDeviceOs();
|
BedrockPlatform device = session.getClientData().getDeviceOs();
|
||||||
userPlatforms.put(device, userPlatforms.getOrDefault(device, 0) + 1);
|
userPlatforms.put(device, userPlatforms.getOrDefault(device, 0) + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -238,8 +237,11 @@ public class DumpInfo {
|
||||||
private final Object config;
|
private final Object config;
|
||||||
|
|
||||||
Floodgate() {
|
Floodgate() {
|
||||||
this.gitInfo = FloodgateInfoHolder.getGitProperties();
|
//todo we can get the information from Floodgate directly now
|
||||||
this.config = FloodgateInfoHolder.getConfig();
|
this.gitInfo = null;
|
||||||
|
this.config = null;
|
||||||
|
// this.gitInfo = FloodgateInfoHolder.getGitProperties();
|
||||||
|
// this.config = FloodgateInfoHolder.getConfig();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -36,7 +36,6 @@ import org.cloudburstmc.nbt.NbtMapBuilder;
|
||||||
import org.cloudburstmc.nbt.NbtType;
|
import org.cloudburstmc.nbt.NbtType;
|
||||||
import org.cloudburstmc.protocol.bedrock.data.entity.EntityDataTypes;
|
import org.cloudburstmc.protocol.bedrock.data.entity.EntityDataTypes;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.SetEntityMotionPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.SetEntityMotionPacket;
|
||||||
import org.geysermc.floodgate.util.DeviceOs;
|
|
||||||
import org.geysermc.geyser.entity.EntityDefinition;
|
import org.geysermc.geyser.entity.EntityDefinition;
|
||||||
import org.geysermc.geyser.entity.type.player.PlayerEntity;
|
import org.geysermc.geyser.entity.type.player.PlayerEntity;
|
||||||
import org.geysermc.geyser.level.FireworkColor;
|
import org.geysermc.geyser.level.FireworkColor;
|
||||||
|
@ -65,13 +64,6 @@ public class FireworkEntity extends Entity {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Remove once Mojang fixes bugs with fireworks crashing clients on these specific devices.
|
|
||||||
// https://bugs.mojang.com/browse/MCPE-89115
|
|
||||||
if (session.getClientData().getDeviceOs() == DeviceOs.XBOX
|
|
||||||
|| session.getClientData().getDeviceOs() == DeviceOs.PS4) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
CompoundTag fireworks = tag.get("Fireworks");
|
CompoundTag fireworks = tag.get("Fireworks");
|
||||||
if (fireworks == null) {
|
if (fireworks == null) {
|
||||||
// Thank you Mineplex very cool
|
// Thank you Mineplex very cool
|
||||||
|
|
|
@ -23,21 +23,18 @@
|
||||||
* @link https://github.com/GeyserMC/Geyser
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.geysermc.floodgate.util;
|
package org.geysermc.geyser.floodgate;
|
||||||
|
|
||||||
public enum UiProfile {
|
import com.google.inject.AbstractModule;
|
||||||
CLASSIC,
|
import com.google.inject.Provides;
|
||||||
POCKET;
|
import com.google.inject.Singleton;
|
||||||
|
import com.google.inject.name.Named;
|
||||||
|
|
||||||
private static final UiProfile[] VALUES = values();
|
public class GeyserLoadStage extends AbstractModule {
|
||||||
|
@Provides
|
||||||
/**
|
@Singleton
|
||||||
* Get the UiProfile instance from the identifier.
|
@Named("configFile")
|
||||||
*
|
private String floodgateConfigName() {
|
||||||
* @param id the UiProfile identifier
|
return "floodgate.yml";
|
||||||
* @return The UiProfile or {@link #CLASSIC} if the UiProfile wasn't found
|
|
||||||
*/
|
|
||||||
public static UiProfile fromId(int id) {
|
|
||||||
return VALUES.length > id ? VALUES[id] : VALUES[0];
|
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -23,51 +23,31 @@
|
||||||
* @link https://github.com/GeyserMC/Geyser
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.geysermc.floodgate.util;
|
package org.geysermc.geyser.hybrid;
|
||||||
|
|
||||||
import lombok.AccessLevel;
|
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
||||||
import lombok.RequiredArgsConstructor;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
/**
|
import java.nio.charset.StandardCharsets;
|
||||||
* The Operation Systems where Bedrock players can connect with
|
|
||||||
*/
|
|
||||||
@RequiredArgsConstructor(access = AccessLevel.PRIVATE)
|
|
||||||
public enum DeviceOs {
|
|
||||||
UNKNOWN("Unknown"),
|
|
||||||
GOOGLE("Android"),
|
|
||||||
IOS("iOS"),
|
|
||||||
OSX("macOS"),
|
|
||||||
AMAZON("Amazon"),
|
|
||||||
GEARVR("Gear VR"),
|
|
||||||
HOLOLENS("Hololens"),
|
|
||||||
UWP("Windows"),
|
|
||||||
WIN32("Windows x86"),
|
|
||||||
DEDICATED("Dedicated"),
|
|
||||||
TVOS("Apple TV"),
|
|
||||||
PS4("PS4"),
|
|
||||||
NX("Switch"),
|
|
||||||
XBOX("Xbox One"),
|
|
||||||
WINDOWS_PHONE("Windows Phone");
|
|
||||||
|
|
||||||
private static final DeviceOs[] VALUES = values();
|
public final class FloodgateHybridProvider implements HybridProvider {
|
||||||
|
private final FloodgateCipher cipher;
|
||||||
|
|
||||||
private final String displayName;
|
public FloodgateHybridProvider(GeyserImpl geyser) {
|
||||||
|
cipher = geyser.getFloodgatePlatform().getInstance(FloodgateCipher.class);
|
||||||
/**
|
|
||||||
* Get the DeviceOs instance from the identifier.
|
|
||||||
*
|
|
||||||
* @param id the DeviceOs identifier
|
|
||||||
* @return The DeviceOs or {@link #UNKNOWN} if the DeviceOs wasn't found
|
|
||||||
*/
|
|
||||||
public static DeviceOs fromId(int id) {
|
|
||||||
return id < VALUES.length ? VALUES[id] : VALUES[0];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @return friendly display name of platform.
|
|
||||||
*/
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public void onSkinUpload(GeyserSession session, String value, String signature) {
|
||||||
return displayName;
|
byte[] bytes = (value + '\0' + signature)
|
||||||
|
.getBytes(StandardCharsets.UTF_8);
|
||||||
|
//todo
|
||||||
|
// PluginMessageUtils.sendMessage(session, PluginMessageChannels.SKIN, bytes);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FloodgateCipher getCipher() {
|
||||||
|
return cipher;
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -0,0 +1,35 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2019-2022 GeyserMC. http://geysermc.org
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* @author GeyserMC
|
||||||
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.geysermc.geyser.hybrid;
|
||||||
|
|
||||||
|
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
|
public interface HybridProvider {
|
||||||
|
void onSkinUpload(GeyserSession session, String value, String signature);
|
||||||
|
|
||||||
|
FloodgateCipher getCipher();
|
||||||
|
}
|
|
@ -0,0 +1,54 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2019-2021 GeyserMC. http://geysermc.org
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* @author GeyserMC
|
||||||
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.geysermc.geyser.hybrid;
|
||||||
|
|
||||||
|
import io.netty.util.AttributeKey;
|
||||||
|
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
||||||
|
import org.geysermc.floodgate.skin.SkinApplier;
|
||||||
|
import org.geysermc.floodgate.skin.SkinData;
|
||||||
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
|
public class IntegratedHybridProvider implements HybridProvider {
|
||||||
|
// TODO This will probably end up as its own class.
|
||||||
|
public static final AttributeKey<GeyserSession> SESSION_KEY = AttributeKey.valueOf("geyser-session");
|
||||||
|
|
||||||
|
private final SkinApplier skinApplier;
|
||||||
|
|
||||||
|
public IntegratedHybridProvider(GeyserImpl geyser) {
|
||||||
|
skinApplier = geyser.getBootstrap().createSkinApplier();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onSkinUpload(GeyserSession session, String value, String signature) {
|
||||||
|
skinApplier.applySkin(session, new SkinData(value, signature));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FloodgateCipher getCipher() {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
}
|
|
@ -23,24 +23,21 @@
|
||||||
* @link https://github.com/GeyserMC/Geyser
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.geysermc.floodgate.util;
|
package org.geysermc.geyser.hybrid;
|
||||||
|
|
||||||
public enum InputMode {
|
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
||||||
UNKNOWN,
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
KEYBOARD_MOUSE,
|
|
||||||
TOUCH,
|
|
||||||
CONTROLLER,
|
|
||||||
VR;
|
|
||||||
|
|
||||||
private static final InputMode[] VALUES = values();
|
public final class ProxyHybridProvider extends IntegratedHybridProvider {
|
||||||
|
private final FloodgateCipher cipher;
|
||||||
|
|
||||||
/**
|
public ProxyHybridProvider(GeyserImpl geyser) {
|
||||||
* Get the InputMode instance from the identifier.
|
super(geyser);
|
||||||
*
|
this.cipher = geyser.getFloodgatePlatform().getInstance(FloodgateCipher.class);
|
||||||
* @param id the InputMode identifier
|
}
|
||||||
* @return The InputMode or {@link #UNKNOWN} if the DeviceOs wasn't found
|
|
||||||
*/
|
@Override
|
||||||
public static InputMode fromId(int id) {
|
public FloodgateCipher getCipher() {
|
||||||
return VALUES.length > id ? VALUES[id] : VALUES[0];
|
return cipher;
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -27,6 +27,10 @@ package org.geysermc.geyser.network.netty;
|
||||||
|
|
||||||
import io.netty.channel.local.LocalChannel;
|
import io.netty.channel.local.LocalChannel;
|
||||||
import io.netty.channel.local.LocalServerChannel;
|
import io.netty.channel.local.LocalServerChannel;
|
||||||
|
import io.netty.util.Attribute;
|
||||||
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.hybrid.IntegratedHybridProvider;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* If the incoming channel if an instance of LocalChannelWithRemoteAddress, this server creates a LocalChannelWrapper
|
* If the incoming channel if an instance of LocalChannelWithRemoteAddress, this server creates a LocalChannelWrapper
|
||||||
|
@ -36,9 +40,17 @@ public class LocalServerChannelWrapper extends LocalServerChannel {
|
||||||
@Override
|
@Override
|
||||||
protected LocalChannel newLocalChannel(LocalChannel peer) {
|
protected LocalChannel newLocalChannel(LocalChannel peer) {
|
||||||
// LocalChannel here should be an instance of LocalChannelWithRemoteAddress, which we can use to set the "remote address" on the other end
|
// LocalChannel here should be an instance of LocalChannelWithRemoteAddress, which we can use to set the "remote address" on the other end
|
||||||
if (peer instanceof LocalChannelWithRemoteAddress) {
|
if (peer instanceof LocalChannelWithRemoteAddress) { // TODO also use attribute for this
|
||||||
LocalChannelWrapper channel = new LocalChannelWrapper(this, peer);
|
LocalChannelWrapper channel = new LocalChannelWrapper(this, peer);
|
||||||
channel.wrapper().remoteAddress(((LocalChannelWithRemoteAddress) peer).spoofedRemoteAddress());
|
channel.wrapper().remoteAddress(((LocalChannelWithRemoteAddress) peer).spoofedRemoteAddress());
|
||||||
|
|
||||||
|
if (GeyserImpl.getInstance().getHybridProvider() instanceof IntegratedHybridProvider) {
|
||||||
|
Attribute<GeyserSession> attribute = peer.attr(IntegratedHybridProvider.SESSION_KEY);
|
||||||
|
GeyserSession session = attribute.get();
|
||||||
|
// Garbage collect since it's no longer relevant for the PacketLib side.
|
||||||
|
attribute.set(null);
|
||||||
|
channel.attr(IntegratedHybridProvider.SESSION_KEY).set(session);
|
||||||
|
}
|
||||||
return channel;
|
return channel;
|
||||||
}
|
}
|
||||||
return super.newLocalChannel(peer);
|
return super.newLocalChannel(peer);
|
||||||
|
|
|
@ -37,7 +37,12 @@ import io.netty.buffer.ByteBufAllocator;
|
||||||
import io.netty.channel.*;
|
import io.netty.channel.*;
|
||||||
import io.netty.channel.unix.PreferredDirectByteBufAllocator;
|
import io.netty.channel.unix.PreferredDirectByteBufAllocator;
|
||||||
import io.netty.handler.codec.haproxy.*;
|
import io.netty.handler.codec.haproxy.*;
|
||||||
|
import io.netty.util.Attribute;
|
||||||
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
|
import org.geysermc.geyser.hybrid.IntegratedHybridProvider;
|
||||||
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
|
||||||
|
import javax.annotation.Nullable;
|
||||||
import java.net.Inet4Address;
|
import java.net.Inet4Address;
|
||||||
import java.net.InetSocketAddress;
|
import java.net.InetSocketAddress;
|
||||||
import java.net.SocketAddress;
|
import java.net.SocketAddress;
|
||||||
|
@ -53,11 +58,14 @@ public final class LocalSession extends TcpSession {
|
||||||
private final String clientIp;
|
private final String clientIp;
|
||||||
private final PacketCodecHelper codecHelper;
|
private final PacketCodecHelper codecHelper;
|
||||||
|
|
||||||
public LocalSession(String host, int port, SocketAddress targetAddress, String clientIp, PacketProtocol protocol, MinecraftCodecHelper codecHelper) {
|
private final GeyserSession session;
|
||||||
|
|
||||||
|
public LocalSession(@Nullable GeyserSession session, String host, int port, SocketAddress targetAddress, String clientIp, PacketProtocol protocol, MinecraftCodecHelper codecHelper) {
|
||||||
super(host, port, protocol);
|
super(host, port, protocol);
|
||||||
this.targetAddress = targetAddress;
|
this.targetAddress = targetAddress;
|
||||||
this.clientIp = clientIp;
|
this.clientIp = clientIp;
|
||||||
this.codecHelper = codecHelper;
|
this.codecHelper = codecHelper;
|
||||||
|
this.session = session;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -89,6 +97,11 @@ public final class LocalSession extends TcpSession {
|
||||||
pipeline.addLast("manager", LocalSession.this);
|
pipeline.addLast("manager", LocalSession.this);
|
||||||
|
|
||||||
addHAProxySupport(pipeline);
|
addHAProxySupport(pipeline);
|
||||||
|
|
||||||
|
if (GeyserImpl.getInstance().getHybridProvider() instanceof IntegratedHybridProvider) {
|
||||||
|
Attribute<GeyserSession> attribute = channel.attr(IntegratedHybridProvider.SESSION_KEY);
|
||||||
|
attribute.set(session);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}).group(DEFAULT_EVENT_LOOP_GROUP).option(ChannelOption.CONNECT_TIMEOUT_MILLIS, getConnectTimeout() * 1000);
|
}).group(DEFAULT_EVENT_LOOP_GROUP).option(ChannelOption.CONNECT_TIMEOUT_MILLIS, getConnectTimeout() * 1000);
|
||||||
|
|
||||||
|
|
|
@ -33,6 +33,7 @@ import org.geysermc.geyser.registry.loader.RegistryLoaders;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.IdentityHashMap;
|
import java.util.IdentityHashMap;
|
||||||
|
|
|
@ -94,7 +94,6 @@ import org.cloudburstmc.protocol.common.util.OptionalBoolean;
|
||||||
import org.geysermc.api.util.BedrockPlatform;
|
import org.geysermc.api.util.BedrockPlatform;
|
||||||
import org.geysermc.api.util.InputMode;
|
import org.geysermc.api.util.InputMode;
|
||||||
import org.geysermc.api.util.UiProfile;
|
import org.geysermc.api.util.UiProfile;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.cumulus.form.Form;
|
import org.geysermc.cumulus.form.Form;
|
||||||
import org.geysermc.cumulus.form.util.FormBuilder;
|
import org.geysermc.cumulus.form.util.FormBuilder;
|
||||||
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
import org.geysermc.floodgate.crypto.FloodgateCipher;
|
||||||
|
@ -116,6 +115,8 @@ import org.geysermc.geyser.entity.type.Tickable;
|
||||||
import org.geysermc.geyser.entity.type.player.SessionPlayerEntity;
|
import org.geysermc.geyser.entity.type.player.SessionPlayerEntity;
|
||||||
import org.geysermc.geyser.erosion.AbstractGeyserboundPacketHandler;
|
import org.geysermc.geyser.erosion.AbstractGeyserboundPacketHandler;
|
||||||
import org.geysermc.geyser.erosion.GeyserboundHandshakePacketHandler;
|
import org.geysermc.geyser.erosion.GeyserboundHandshakePacketHandler;
|
||||||
|
import org.geysermc.geyser.hybrid.FloodgateHybridProvider;
|
||||||
|
import org.geysermc.geyser.hybrid.HybridProvider;
|
||||||
import org.geysermc.geyser.inventory.Inventory;
|
import org.geysermc.geyser.inventory.Inventory;
|
||||||
import org.geysermc.geyser.inventory.PlayerInventory;
|
import org.geysermc.geyser.inventory.PlayerInventory;
|
||||||
import org.geysermc.geyser.inventory.recipe.GeyserRecipe;
|
import org.geysermc.geyser.inventory.recipe.GeyserRecipe;
|
||||||
|
@ -131,15 +132,13 @@ import org.geysermc.geyser.registry.type.ItemMappings;
|
||||||
import org.geysermc.geyser.session.auth.AuthData;
|
import org.geysermc.geyser.session.auth.AuthData;
|
||||||
import org.geysermc.geyser.session.auth.BedrockClientData;
|
import org.geysermc.geyser.session.auth.BedrockClientData;
|
||||||
import org.geysermc.geyser.session.cache.*;
|
import org.geysermc.geyser.session.cache.*;
|
||||||
import org.geysermc.geyser.skin.FloodgateSkinUploader;
|
import org.geysermc.geyser.skin.BedrockSkinUploader;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.text.MinecraftLocale;
|
import org.geysermc.geyser.text.MinecraftLocale;
|
||||||
import org.geysermc.geyser.text.TextDecoration;
|
import org.geysermc.geyser.text.TextDecoration;
|
||||||
import org.geysermc.geyser.translator.inventory.InventoryTranslator;
|
import org.geysermc.geyser.translator.inventory.InventoryTranslator;
|
||||||
import org.geysermc.geyser.translator.text.MessageTranslator;
|
import org.geysermc.geyser.translator.text.MessageTranslator;
|
||||||
import org.geysermc.geyser.util.ChunkUtils;
|
import org.geysermc.geyser.util.*;
|
||||||
import org.geysermc.geyser.util.DimensionUtils;
|
|
||||||
import org.geysermc.geyser.util.LoginEncryptionUtils;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.net.ConnectException;
|
import java.net.ConnectException;
|
||||||
|
@ -886,7 +885,7 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
|
||||||
TcpSession downstream;
|
TcpSession downstream;
|
||||||
if (geyser.getBootstrap().getSocketAddress() != null) {
|
if (geyser.getBootstrap().getSocketAddress() != null) {
|
||||||
// We're going to connect through the JVM and not through TCP
|
// We're going to connect through the JVM and not through TCP
|
||||||
downstream = new LocalSession(this.remoteServer.address(), this.remoteServer.port(),
|
downstream = new LocalSession(this, this.remoteServer.address(), this.remoteServer.port(),
|
||||||
geyser.getBootstrap().getSocketAddress(), upstream.getAddress().getAddress().getHostAddress(),
|
geyser.getBootstrap().getSocketAddress(), upstream.getAddress().getAddress().getHostAddress(),
|
||||||
this.protocol, this.protocol.createHelper());
|
this.protocol, this.protocol.createHelper());
|
||||||
this.downstream = new DownstreamSession(downstream);
|
this.downstream = new DownstreamSession(downstream);
|
||||||
|
@ -910,12 +909,13 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
|
||||||
//todo move this somewhere else
|
//todo move this somewhere else
|
||||||
if (event.getPacket() instanceof ClientIntentionPacket) {
|
if (event.getPacket() instanceof ClientIntentionPacket) {
|
||||||
String addressSuffix;
|
String addressSuffix;
|
||||||
if (floodgate) {
|
HybridProvider provider;
|
||||||
|
if (floodgate && (provider = geyser.getHybridProvider()) instanceof FloodgateHybridProvider) {
|
||||||
byte[] encryptedData;
|
byte[] encryptedData;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
FloodgateSkinUploader skinUploader = geyser.getSkinUploader();
|
BedrockSkinUploader skinUploader = geyser.getSkinUploader();
|
||||||
FloodgateCipher cipher = geyser.getCipher();
|
FloodgateCipher cipher = provider.getCipher();
|
||||||
|
|
||||||
String bedrockAddress = upstream.getAddress().getAddress().getHostAddress();
|
String bedrockAddress = upstream.getAddress().getAddress().getHostAddress();
|
||||||
// both BungeeCord and Velocity remove the IPv6 scope (if there is one) for Spigot
|
// both BungeeCord and Velocity remove the IPv6 scope (if there is one) for Spigot
|
||||||
|
@ -1434,7 +1434,8 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
|
||||||
upstream.sendPacket(chunkRadiusUpdatedPacket);
|
upstream.sendPacket(chunkRadiusUpdatedPacket);
|
||||||
}
|
}
|
||||||
|
|
||||||
public InetSocketAddress getSocketAddress() {
|
@Override
|
||||||
|
public InetSocketAddress socketAddress() {
|
||||||
return this.upstream.getAddress();
|
return this.upstream.getAddress();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1885,7 +1886,7 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public @NonNull BedrockPlatform platform() {
|
public @NonNull BedrockPlatform platform() {
|
||||||
return BedrockPlatform.values()[clientData.getDeviceOs().ordinal()]; //todo
|
return clientData.getDeviceOs();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -1895,12 +1896,12 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public @NonNull UiProfile uiProfile() {
|
public @NonNull UiProfile uiProfile() {
|
||||||
return UiProfile.values()[clientData.getUiProfile().ordinal()]; //todo
|
return clientData.getUiProfile();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public @NonNull InputMode inputMode() {
|
public @NonNull InputMode inputMode() {
|
||||||
return InputMode.values()[clientData.getCurrentInputMode().ordinal()]; //todo
|
return clientData.getCurrentInputMode();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -30,9 +30,9 @@ import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
import org.geysermc.floodgate.util.DeviceOs;
|
import org.geysermc.api.util.BedrockPlatform;
|
||||||
import org.geysermc.floodgate.util.InputMode;
|
import org.geysermc.api.util.InputMode;
|
||||||
import org.geysermc.floodgate.util.UiProfile;
|
import org.geysermc.api.util.UiProfile;
|
||||||
|
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
@ -80,7 +80,7 @@ public final class BedrockClientData {
|
||||||
@JsonProperty(value = "DeviceModel")
|
@JsonProperty(value = "DeviceModel")
|
||||||
private String deviceModel;
|
private String deviceModel;
|
||||||
@JsonProperty(value = "DeviceOS")
|
@JsonProperty(value = "DeviceOS")
|
||||||
private DeviceOs deviceOs;
|
private BedrockPlatform deviceOs;
|
||||||
@JsonProperty(value = "UIProfile")
|
@JsonProperty(value = "UIProfile")
|
||||||
private UiProfile uiProfile;
|
private UiProfile uiProfile;
|
||||||
@JsonProperty(value = "GuiScale")
|
@JsonProperty(value = "GuiScale")
|
||||||
|
@ -113,8 +113,8 @@ public final class BedrockClientData {
|
||||||
@Setter
|
@Setter
|
||||||
private String originalString = null;
|
private String originalString = null;
|
||||||
|
|
||||||
public DeviceOs getDeviceOs() {
|
public BedrockPlatform getDeviceOs() {
|
||||||
return deviceOs != null ? deviceOs : DeviceOs.UNKNOWN;
|
return deviceOs != null ? deviceOs : BedrockPlatform.UNKNOWN;
|
||||||
}
|
}
|
||||||
|
|
||||||
public InputMode getCurrentInputMode() {
|
public InputMode getCurrentInputMode() {
|
||||||
|
|
|
@ -32,26 +32,23 @@ import com.fasterxml.jackson.databind.node.ArrayNode;
|
||||||
import com.fasterxml.jackson.databind.node.ObjectNode;
|
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||||
import com.nimbusds.jwt.SignedJWT;
|
import com.nimbusds.jwt.SignedJWT;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import org.geysermc.floodgate.pluginmessage.PluginMessageChannels;
|
|
||||||
import org.geysermc.floodgate.util.WebsocketEventType;
|
import org.geysermc.floodgate.util.WebsocketEventType;
|
||||||
import org.geysermc.geyser.Constants;
|
import org.geysermc.geyser.Constants;
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.GeyserLogger;
|
import org.geysermc.geyser.GeyserLogger;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.util.PluginMessageUtils;
|
|
||||||
import org.java_websocket.client.WebSocketClient;
|
import org.java_websocket.client.WebSocketClient;
|
||||||
import org.java_websocket.handshake.ServerHandshake;
|
import org.java_websocket.handshake.ServerHandshake;
|
||||||
|
|
||||||
import javax.net.ssl.SSLException;
|
import javax.net.ssl.SSLException;
|
||||||
import java.net.ConnectException;
|
import java.net.ConnectException;
|
||||||
import java.nio.charset.StandardCharsets;
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.concurrent.ThreadLocalRandom;
|
import java.util.concurrent.ThreadLocalRandom;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
public final class FloodgateSkinUploader {
|
public final class BedrockSkinUploader {
|
||||||
private final ObjectMapper JACKSON = new ObjectMapper();
|
private final ObjectMapper JACKSON = new ObjectMapper();
|
||||||
private final List<String> skinQueue = new ArrayList<>();
|
private final List<String> skinQueue = new ArrayList<>();
|
||||||
|
|
||||||
|
@ -61,9 +58,8 @@ public final class FloodgateSkinUploader {
|
||||||
|
|
||||||
@Getter private int id;
|
@Getter private int id;
|
||||||
@Getter private String verifyCode;
|
@Getter private String verifyCode;
|
||||||
@Getter private int subscribersCount;
|
|
||||||
|
|
||||||
public FloodgateSkinUploader(GeyserImpl geyser) {
|
public BedrockSkinUploader(GeyserImpl geyser) {
|
||||||
this.logger = geyser.getLogger();
|
this.logger = geyser.getLogger();
|
||||||
this.client = new WebSocketClient(Constants.GLOBAL_API_WS_URI) {
|
this.client = new WebSocketClient(Constants.GLOBAL_API_WS_URI) {
|
||||||
@Override
|
@Override
|
||||||
|
@ -102,14 +98,11 @@ public final class FloodgateSkinUploader {
|
||||||
verifyCode = node.get("verify_code").asText();
|
verifyCode = node.get("verify_code").asText();
|
||||||
break;
|
break;
|
||||||
case SUBSCRIBER_COUNT:
|
case SUBSCRIBER_COUNT:
|
||||||
subscribersCount = node.get("subscribers_count").asInt();
|
logger.debug("Ignoring subscribers count message.");
|
||||||
break;
|
break;
|
||||||
case SKIN_UPLOADED:
|
case SKIN_UPLOADED:
|
||||||
// if Geyser is the only subscriber we have send it to the server manually
|
// if Geyser is the only subscriber we have send it to the server manually
|
||||||
// otherwise it's handled by the Floodgate plugin subscribers
|
// otherwise it's handled by the Floodgate plugin subscribers
|
||||||
if (subscribersCount != 1) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
String xuid = node.get("xuid").asText();
|
String xuid = node.get("xuid").asText();
|
||||||
GeyserSession session = geyser.connectionByXuid(xuid);
|
GeyserSession session = geyser.connectionByXuid(xuid);
|
||||||
|
@ -125,9 +118,7 @@ public final class FloodgateSkinUploader {
|
||||||
String value = data.get("value").asText();
|
String value = data.get("value").asText();
|
||||||
String signature = data.get("signature").asText();
|
String signature = data.get("signature").asText();
|
||||||
|
|
||||||
byte[] bytes = (value + '\0' + signature)
|
geyser.getHybridProvider().onSkinUpload(session, value, signature);
|
||||||
.getBytes(StandardCharsets.UTF_8);
|
|
||||||
PluginMessageUtils.sendMessage(session, PluginMessageChannels.SKIN, bytes);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case LOG_MESSAGE:
|
case LOG_MESSAGE:
|
||||||
|
@ -226,7 +217,7 @@ public final class FloodgateSkinUploader {
|
||||||
.schedule(client::reconnect, 8 + additionalTime, TimeUnit.SECONDS);
|
.schedule(client::reconnect, 8 + additionalTime, TimeUnit.SECONDS);
|
||||||
}
|
}
|
||||||
|
|
||||||
public FloodgateSkinUploader start() {
|
public BedrockSkinUploader start() {
|
||||||
client.connect();
|
client.connect();
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
|
@ -36,7 +36,6 @@ import it.unimi.dsi.fastutil.objects.Object2IntMap;
|
||||||
import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
|
import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
|
||||||
import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet;
|
import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.level.block.BlockStateValues;
|
import org.geysermc.geyser.level.block.BlockStateValues;
|
||||||
import org.geysermc.geyser.level.physics.Axis;
|
import org.geysermc.geyser.level.physics.Axis;
|
||||||
import org.geysermc.geyser.level.physics.BoundingBox;
|
import org.geysermc.geyser.level.physics.BoundingBox;
|
||||||
|
@ -50,6 +49,7 @@ import org.geysermc.geyser.translator.collision.BlockCollision;
|
||||||
import org.geysermc.geyser.util.BlockEntityUtils;
|
import org.geysermc.geyser.util.BlockEntityUtils;
|
||||||
import org.geysermc.geyser.util.BlockUtils;
|
import org.geysermc.geyser.util.BlockUtils;
|
||||||
import org.geysermc.geyser.util.ChunkUtils;
|
import org.geysermc.geyser.util.ChunkUtils;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.LinkedList;
|
import java.util.LinkedList;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
|
@ -26,13 +26,13 @@
|
||||||
package org.geysermc.geyser.translator.protocol.bedrock;
|
package org.geysermc.geyser.translator.protocol.bedrock;
|
||||||
|
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.CommandRequestPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.CommandRequestPacket;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.ChatColor;
|
import org.geysermc.geyser.text.ChatColor;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
import org.geysermc.geyser.translator.protocol.Translator;
|
import org.geysermc.geyser.translator.protocol.Translator;
|
||||||
import org.geysermc.geyser.translator.text.MessageTranslator;
|
import org.geysermc.geyser.translator.text.MessageTranslator;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
@Translator(packet = CommandRequestPacket.class)
|
@Translator(packet = CommandRequestPacket.class)
|
||||||
public class BedrockCommandRequestTranslator extends PacketTranslator<CommandRequestPacket> {
|
public class BedrockCommandRequestTranslator extends PacketTranslator<CommandRequestPacket> {
|
||||||
|
|
|
@ -29,7 +29,7 @@ import com.github.steveice10.mc.protocol.packet.ingame.serverbound.ServerboundKe
|
||||||
import org.cloudburstmc.protocol.bedrock.data.AttributeData;
|
import org.cloudburstmc.protocol.bedrock.data.AttributeData;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.NetworkStackLatencyPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.NetworkStackLatencyPacket;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.UpdateAttributesPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.UpdateAttributesPacket;
|
||||||
import org.geysermc.floodgate.util.DeviceOs;
|
import org.geysermc.api.util.BedrockPlatform;
|
||||||
import org.geysermc.geyser.entity.attribute.GeyserAttributeType;
|
import org.geysermc.geyser.entity.attribute.GeyserAttributeType;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
|
@ -50,7 +50,7 @@ public class BedrockNetworkStackLatencyTranslator extends PacketTranslator<Netwo
|
||||||
// so apparently, as of 1.16.200
|
// so apparently, as of 1.16.200
|
||||||
// PS4 divides the network stack latency timestamp FOR US!!!
|
// PS4 divides the network stack latency timestamp FOR US!!!
|
||||||
// WTF
|
// WTF
|
||||||
if (session.getClientData().getDeviceOs().equals(DeviceOs.PS4)) {
|
if (session.getClientData().getDeviceOs() == BedrockPlatform.PS4) {
|
||||||
pingId = packet.getTimestamp();
|
pingId = packet.getTimestamp();
|
||||||
} else {
|
} else {
|
||||||
pingId = packet.getTimestamp() / 1000;
|
pingId = packet.getTimestamp() / 1000;
|
||||||
|
|
|
@ -26,28 +26,12 @@
|
||||||
package org.geysermc.geyser.translator.protocol.java;
|
package org.geysermc.geyser.translator.protocol.java;
|
||||||
|
|
||||||
import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundCustomPayloadPacket;
|
import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundCustomPayloadPacket;
|
||||||
import com.github.steveice10.mc.protocol.packet.ingame.serverbound.ServerboundCustomPayloadPacket;
|
|
||||||
import com.google.common.base.Charsets;
|
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.TransferPacket;
|
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.UnknownPacket;
|
|
||||||
import io.netty.buffer.ByteBuf;
|
|
||||||
import io.netty.buffer.Unpooled;
|
|
||||||
import org.geysermc.cumulus.Forms;
|
|
||||||
import org.geysermc.cumulus.form.Form;
|
|
||||||
import org.geysermc.cumulus.form.util.FormType;
|
|
||||||
import org.geysermc.erosion.Constants;
|
|
||||||
import org.geysermc.erosion.packet.ErosionPacket;
|
|
||||||
import org.geysermc.erosion.packet.Packets;
|
|
||||||
import org.geysermc.erosion.packet.geyserbound.GeyserboundPacket;
|
|
||||||
import org.geysermc.floodgate.pluginmessage.PluginMessageChannels;
|
|
||||||
import org.geysermc.geyser.GeyserImpl;
|
import org.geysermc.geyser.GeyserImpl;
|
||||||
import org.geysermc.geyser.GeyserLogger;
|
import org.geysermc.geyser.GeyserLogger;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
import org.geysermc.geyser.translator.protocol.Translator;
|
import org.geysermc.geyser.translator.protocol.Translator;
|
||||||
|
|
||||||
import java.nio.charset.StandardCharsets;
|
|
||||||
|
|
||||||
@Translator(packet = ClientboundCustomPayloadPacket.class)
|
@Translator(packet = ClientboundCustomPayloadPacket.class)
|
||||||
public class JavaCustomPayloadTranslator extends PacketTranslator<ClientboundCustomPayloadPacket> {
|
public class JavaCustomPayloadTranslator extends PacketTranslator<ClientboundCustomPayloadPacket> {
|
||||||
private final GeyserLogger logger = GeyserImpl.getInstance().getLogger();
|
private final GeyserLogger logger = GeyserImpl.getInstance().getLogger();
|
||||||
|
@ -56,89 +40,89 @@ public class JavaCustomPayloadTranslator extends PacketTranslator<ClientboundCus
|
||||||
public void translate(GeyserSession session, ClientboundCustomPayloadPacket packet) {
|
public void translate(GeyserSession session, ClientboundCustomPayloadPacket packet) {
|
||||||
String channel = packet.getChannel();
|
String channel = packet.getChannel();
|
||||||
|
|
||||||
if (channel.equals(Constants.PLUGIN_MESSAGE)) {
|
// if (channel.equals(Constants.PLUGIN_MESSAGE)) {
|
||||||
ByteBuf buf = Unpooled.wrappedBuffer(packet.getData());
|
// ByteBuf buf = Unpooled.wrappedBuffer(packet.getData());
|
||||||
ErosionPacket<?> erosionPacket = Packets.decode(buf);
|
// ErosionPacket<?> erosionPacket = Packets.decode(buf);
|
||||||
((GeyserboundPacket) erosionPacket).handle(session.getErosionHandler());
|
// ((GeyserboundPacket) erosionPacket).handle(session.getErosionHandler());
|
||||||
return;
|
// return;
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
if (channel.equals(PluginMessageChannels.FORM)) {
|
// if (channel.equals(PluginMessageChannels.FORM)) {
|
||||||
session.ensureInEventLoop(() -> {
|
// session.ensureInEventLoop(() -> {
|
||||||
byte[] data = packet.getData();
|
// byte[] data = packet.getData();
|
||||||
|
//
|
||||||
// receive: first byte is form type, second and third are the id, remaining is the form data
|
// // receive: first byte is form type, second and third are the id, remaining is the form data
|
||||||
// respond: first and second byte id, remaining is form response data
|
// // respond: first and second byte id, remaining is form response data
|
||||||
|
//
|
||||||
FormType type = FormType.fromOrdinal(data[0]);
|
// FormType type = FormType.fromOrdinal(data[0]);
|
||||||
if (type == null) {
|
// if (type == null) {
|
||||||
throw new NullPointerException("Got type " + data[0] + " which isn't a valid form type!");
|
// throw new NullPointerException("Got type " + data[0] + " which isn't a valid form type!");
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
String dataString = new String(data, 3, data.length - 3, Charsets.UTF_8);
|
// String dataString = new String(data, 3, data.length - 3, Charsets.UTF_8);
|
||||||
|
//
|
||||||
Form form = Forms.fromJson(dataString, type, (ignored, response) -> {
|
// Form form = Forms.fromJson(dataString, type, (ignored, response) -> {
|
||||||
byte[] finalData;
|
// byte[] finalData;
|
||||||
if (response == null) {
|
// if (response == null) {
|
||||||
// Response data can be null as of 1.19.20 (same behaviour as empty response data)
|
// // Response data can be null as of 1.19.20 (same behaviour as empty response data)
|
||||||
// Only need to send the form id
|
// // Only need to send the form id
|
||||||
finalData = new byte[]{data[1], data[2]};
|
// finalData = new byte[]{data[1], data[2]};
|
||||||
} else {
|
// } else {
|
||||||
byte[] raw = response.getBytes(StandardCharsets.UTF_8);
|
// byte[] raw = response.getBytes(StandardCharsets.UTF_8);
|
||||||
finalData = new byte[raw.length + 2];
|
// finalData = new byte[raw.length + 2];
|
||||||
|
//
|
||||||
finalData[0] = data[1];
|
// finalData[0] = data[1];
|
||||||
finalData[1] = data[2];
|
// finalData[1] = data[2];
|
||||||
System.arraycopy(raw, 0, finalData, 2, raw.length);
|
// System.arraycopy(raw, 0, finalData, 2, raw.length);
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
session.sendDownstreamPacket(new ServerboundCustomPayloadPacket(channel, finalData));
|
// session.sendDownstreamPacket(new ServerboundCustomPayloadPacket(channel, finalData));
|
||||||
});
|
// });
|
||||||
session.sendForm(form);
|
// session.sendForm(form);
|
||||||
});
|
// });
|
||||||
|
//
|
||||||
} else if (channel.equals(PluginMessageChannels.TRANSFER)) {
|
// } else if (channel.equals(PluginMessageChannels.TRANSFER)) {
|
||||||
session.ensureInEventLoop(() -> {
|
// session.ensureInEventLoop(() -> {
|
||||||
byte[] data = packet.getData();
|
// byte[] data = packet.getData();
|
||||||
|
//
|
||||||
// port (4 bytes), address (remaining data)
|
// // port (4 bytes), address (remaining data)
|
||||||
if (data.length < 5) {
|
// if (data.length < 5) {
|
||||||
throw new NullPointerException("Transfer data should be at least 5 bytes long");
|
// throw new NullPointerException("Transfer data should be at least 5 bytes long");
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
int port = data[0] << 24 | (data[1] & 0xFF) << 16 | (data[2] & 0xFF) << 8 | data[3] & 0xFF;
|
// int port = data[0] << 24 | (data[1] & 0xFF) << 16 | (data[2] & 0xFF) << 8 | data[3] & 0xFF;
|
||||||
String address = new String(data, 4, data.length - 4);
|
// String address = new String(data, 4, data.length - 4);
|
||||||
|
//
|
||||||
if (logger.isDebug()) {
|
// if (logger.isDebug()) {
|
||||||
logger.info("Transferring client to: " + address + ":" + port);
|
// logger.info("Transferring client to: " + address + ":" + port);
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
TransferPacket transferPacket = new TransferPacket();
|
// TransferPacket transferPacket = new TransferPacket();
|
||||||
transferPacket.setAddress(address);
|
// transferPacket.setAddress(address);
|
||||||
transferPacket.setPort(port);
|
// transferPacket.setPort(port);
|
||||||
session.sendUpstreamPacket(transferPacket);
|
// session.sendUpstreamPacket(transferPacket);
|
||||||
});
|
// });
|
||||||
|
//
|
||||||
} else if (channel.equals(PluginMessageChannels.PACKET)) {
|
// } else if (channel.equals(PluginMessageChannels.PACKET)) {
|
||||||
session.ensureInEventLoop(() -> {
|
// session.ensureInEventLoop(() -> {
|
||||||
logger.debug("A packet has been sent using the Floodgate api");
|
// logger.debug("A packet has been sent using the Floodgate api");
|
||||||
byte[] data = packet.getData();
|
// byte[] data = packet.getData();
|
||||||
|
//
|
||||||
// packet id, packet data
|
// // packet id, packet data
|
||||||
if (data.length < 2) {
|
// if (data.length < 2) {
|
||||||
throw new IllegalStateException("Packet data should be at least 2 bytes long");
|
// throw new IllegalStateException("Packet data should be at least 2 bytes long");
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
int packetId = data[0] & 0xFF;
|
// int packetId = data[0] & 0xFF;
|
||||||
ByteBuf packetData = Unpooled.wrappedBuffer(data, 1, data.length - 1);
|
// ByteBuf packetData = Unpooled.wrappedBuffer(data, 1, data.length - 1);
|
||||||
|
//
|
||||||
var toSend = new UnknownPacket();
|
// var toSend = new UnknownPacket();
|
||||||
toSend.setPacketId(packetId);
|
// toSend.setPacketId(packetId);
|
||||||
toSend.setPayload(packetData);
|
// toSend.setPayload(packetData);
|
||||||
|
//
|
||||||
session.sendUpstreamPacket(toSend);
|
// session.sendUpstreamPacket(toSend);
|
||||||
});
|
// });
|
||||||
}
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -29,13 +29,13 @@ import com.github.steveice10.mc.protocol.packet.login.clientbound.ClientboundLog
|
||||||
import net.kyori.adventure.text.Component;
|
import net.kyori.adventure.text.Component;
|
||||||
import net.kyori.adventure.text.TextComponent;
|
import net.kyori.adventure.text.TextComponent;
|
||||||
import net.kyori.adventure.text.TranslatableComponent;
|
import net.kyori.adventure.text.TranslatableComponent;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.network.GameProtocol;
|
import org.geysermc.geyser.network.GameProtocol;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.text.GeyserLocale;
|
import org.geysermc.geyser.text.GeyserLocale;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
import org.geysermc.geyser.translator.protocol.Translator;
|
import org.geysermc.geyser.translator.protocol.Translator;
|
||||||
import org.geysermc.geyser.translator.text.MessageTranslator;
|
import org.geysermc.geyser.translator.text.MessageTranslator;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
|
@ -33,7 +33,6 @@ import org.cloudburstmc.protocol.bedrock.data.GameRuleData;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.GameRulesChangedPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.GameRulesChangedPacket;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.SetPlayerGameTypePacket;
|
import org.cloudburstmc.protocol.bedrock.packet.SetPlayerGameTypePacket;
|
||||||
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
||||||
import org.geysermc.floodgate.pluginmessage.PluginMessageChannels;
|
|
||||||
import org.geysermc.geyser.api.network.AuthType;
|
import org.geysermc.geyser.api.network.AuthType;
|
||||||
import org.geysermc.geyser.entity.type.player.SessionPlayerEntity;
|
import org.geysermc.geyser.entity.type.player.SessionPlayerEntity;
|
||||||
import org.geysermc.geyser.erosion.GeyserboundHandshakePacketHandler;
|
import org.geysermc.geyser.erosion.GeyserboundHandshakePacketHandler;
|
||||||
|
@ -141,7 +140,8 @@ public class JavaLoginTranslator extends PacketTranslator<ClientboundLoginPacket
|
||||||
// }
|
// }
|
||||||
// register the plugin messaging channels used in Floodgate
|
// register the plugin messaging channels used in Floodgate
|
||||||
if (session.remoteServer().authType() == AuthType.FLOODGATE) {
|
if (session.remoteServer().authType() == AuthType.FLOODGATE) {
|
||||||
session.sendDownstreamPacket(new ServerboundCustomPayloadPacket("minecraft:register", PluginMessageChannels.getFloodgateRegisterData()));
|
//todo
|
||||||
|
// session.sendDownstreamPacket(new ServerboundCustomPayloadPacket("minecraft:register", PluginMessageChannels.getFloodgateRegisterData()));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!newDimension.equals(session.getDimension())) {
|
if (!newDimension.equals(session.getDimension())) {
|
||||||
|
|
|
@ -33,7 +33,6 @@ import org.cloudburstmc.nbt.NbtMapBuilder;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.BlockEntityDataPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.BlockEntityDataPacket;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.BlockEventPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.BlockEventPacket;
|
||||||
import it.unimi.dsi.fastutil.objects.Object2IntMaps;
|
import it.unimi.dsi.fastutil.objects.Object2IntMaps;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.level.block.BlockStateValues;
|
import org.geysermc.geyser.level.block.BlockStateValues;
|
||||||
import org.geysermc.geyser.level.physics.Direction;
|
import org.geysermc.geyser.level.physics.Direction;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
|
@ -41,6 +40,7 @@ import org.geysermc.geyser.session.cache.PistonCache;
|
||||||
import org.geysermc.geyser.translator.level.block.entity.PistonBlockEntity;
|
import org.geysermc.geyser.translator.level.block.entity.PistonBlockEntity;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
import org.geysermc.geyser.translator.protocol.Translator;
|
import org.geysermc.geyser.translator.protocol.Translator;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
@Translator(packet = ClientboundBlockEventPacket.class)
|
@Translator(packet = ClientboundBlockEventPacket.class)
|
||||||
public class JavaBlockEventTranslator extends PacketTranslator<ClientboundBlockEventPacket> {
|
public class JavaBlockEventTranslator extends PacketTranslator<ClientboundBlockEventPacket> {
|
||||||
|
|
|
@ -29,13 +29,13 @@ import com.github.steveice10.mc.protocol.packet.ingame.clientbound.level.Clientb
|
||||||
import org.cloudburstmc.math.vector.Vector3i;
|
import org.cloudburstmc.math.vector.Vector3i;
|
||||||
import org.cloudburstmc.protocol.bedrock.data.SoundEvent;
|
import org.cloudburstmc.protocol.bedrock.data.SoundEvent;
|
||||||
import org.cloudburstmc.protocol.bedrock.packet.LevelSoundEventPacket;
|
import org.cloudburstmc.protocol.bedrock.packet.LevelSoundEventPacket;
|
||||||
import org.geysermc.common.PlatformType;
|
|
||||||
import org.geysermc.geyser.registry.BlockRegistries;
|
import org.geysermc.geyser.registry.BlockRegistries;
|
||||||
import org.geysermc.geyser.registry.type.BlockMapping;
|
import org.geysermc.geyser.registry.type.BlockMapping;
|
||||||
import org.geysermc.geyser.session.GeyserSession;
|
import org.geysermc.geyser.session.GeyserSession;
|
||||||
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
import org.geysermc.geyser.translator.protocol.PacketTranslator;
|
||||||
import org.geysermc.geyser.translator.protocol.Translator;
|
import org.geysermc.geyser.translator.protocol.Translator;
|
||||||
import org.geysermc.geyser.translator.sound.BlockSoundInteractionTranslator;
|
import org.geysermc.geyser.translator.sound.BlockSoundInteractionTranslator;
|
||||||
|
import org.geysermc.geyser.util.PlatformType;
|
||||||
|
|
||||||
@Translator(packet = ClientboundBlockUpdatePacket.class)
|
@Translator(packet = ClientboundBlockUpdatePacket.class)
|
||||||
public class JavaBlockUpdateTranslator extends PacketTranslator<ClientboundBlockUpdatePacket> {
|
public class JavaBlockUpdateTranslator extends PacketTranslator<ClientboundBlockUpdatePacket> {
|
||||||
|
|
|
@ -23,7 +23,7 @@
|
||||||
* @link https://github.com/GeyserMC/Geyser
|
* @link https://github.com/GeyserMC/Geyser
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package org.geysermc.common;
|
package org.geysermc.geyser.util;
|
||||||
|
|
||||||
import lombok.AllArgsConstructor;
|
import lombok.AllArgsConstructor;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
|
@ -212,12 +212,6 @@ enable-proxy-connections: false
|
||||||
# 1400 is the default.
|
# 1400 is the default.
|
||||||
mtu: 1400
|
mtu: 1400
|
||||||
|
|
||||||
# Whether to connect directly into the Java server without creating a TCP connection.
|
|
||||||
# This should only be disabled if a plugin that interfaces with packets or the network does not work correctly with Geyser.
|
|
||||||
# If enabled on plugin versions, the remote address and port sections are ignored
|
|
||||||
# If disabled on plugin versions, expect performance decrease and latency increase
|
|
||||||
use-direct-connection: true
|
|
||||||
|
|
||||||
# Whether Geyser should attempt to disable compression for Bedrock players. This should be a benefit as there is no need to compress data
|
# Whether Geyser should attempt to disable compression for Bedrock players. This should be a benefit as there is no need to compress data
|
||||||
# when Java packets aren't being handled over the network.
|
# when Java packets aren't being handled over the network.
|
||||||
# This requires use-direct-connection to be true.
|
# This requires use-direct-connection to be true.
|
||||||
|
|
|
@ -5,8 +5,6 @@ org.gradle.caching=true
|
||||||
org.gradle.parallel=true
|
org.gradle.parallel=true
|
||||||
|
|
||||||
group=org.geysermc
|
group=org.geysermc
|
||||||
version=2.1.0-SNAPSHOT
|
version=3.0.0-SNAPSHOT
|
||||||
|
|
||||||
org.gradle.caching=true
|
|
||||||
org.gradle.parallel=true
|
|
||||||
org.gradle.vfs.watch=false
|
org.gradle.vfs.watch=false
|
|
@ -3,6 +3,7 @@ enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS")
|
||||||
dependencyResolutionManagement {
|
dependencyResolutionManagement {
|
||||||
// repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS)
|
// repositoriesMode.set(RepositoriesMode.FAIL_ON_PROJECT_REPOS)
|
||||||
repositories {
|
repositories {
|
||||||
|
mavenLocal()
|
||||||
// Floodgate, Cumulus etc.
|
// Floodgate, Cumulus etc.
|
||||||
maven("https://repo.opencollab.dev/main")
|
maven("https://repo.opencollab.dev/main")
|
||||||
|
|
||||||
|
@ -24,7 +25,6 @@ dependencyResolutionManagement {
|
||||||
mavenContent { releasesOnly() }
|
mavenContent { releasesOnly() }
|
||||||
}
|
}
|
||||||
|
|
||||||
mavenLocal()
|
|
||||||
mavenCentral()
|
mavenCentral()
|
||||||
|
|
||||||
// ViaVersion
|
// ViaVersion
|
||||||
|
|
Loading…
Reference in a new issue