package com.mojang.realmsclient.client; import org.apache.logging.log4j.LogManager; import com.mojang.realmsclient.exception.RealmsHttpException; import com.mojang.realmsclient.exception.RetryCallException; import java.net.URISyntaxException; import java.net.URI; import com.mojang.realmsclient.dto.PingResult; import com.mojang.realmsclient.dto.RealmsNews; import com.google.gson.GsonBuilder; import com.mojang.realmsclient.dto.UploadInfo; import com.mojang.realmsclient.dto.WorldDownload; import com.mojang.realmsclient.dto.PendingInvitesList; import com.mojang.realmsclient.dto.Subscription; import com.mojang.realmsclient.dto.RealmsWorldResetDto; import com.mojang.realmsclient.dto.Ops; import com.mojang.realmsclient.dto.WorldTemplatePaginatedList; import com.mojang.realmsclient.dto.RealmsWorldOptions; import java.io.UnsupportedEncodingException; import com.mojang.realmsclient.dto.BackupList; import com.mojang.realmsclient.dto.PlayerInfo; import com.mojang.realmsclient.dto.RealmsDescriptionDto; import com.mojang.realmsclient.dto.RealmsServerAddress; import com.mojang.realmsclient.dto.RealmsServerPlayerLists; import com.mojang.realmsclient.dto.RealmsServer; import java.io.IOException; import com.mojang.realmsclient.exception.RealmsServiceException; import com.mojang.realmsclient.dto.RealmsServerList; import java.net.Proxy; import net.minecraft.realms.Realms; import com.google.gson.Gson; import org.apache.logging.log4j.Logger; public class RealmsClient { public static Environment currentEnvironment; private static boolean initialized; private static final Logger LOGGER; private final String sessionId; private final String username; private static final Gson gson; public static RealmsClient createRealmsClient() { final String string1 = Realms.userName(); final String string2 = Realms.sessionId(); if (string1 == null || string2 == null) { return null; } if (!RealmsClient.initialized) { RealmsClient.initialized = true; String string3 = System.getenv("realms.environment"); if (string3 == null) { string3 = System.getProperty("realms.environment"); } if (string3 != null) { if ("LOCAL".equals(string3)) { switchToLocal(); } else if ("STAGE".equals(string3)) { switchToStage(); } } } return new RealmsClient(string2, string1, Realms.getProxy()); } public static void switchToStage() { RealmsClient.currentEnvironment = Environment.STAGE; } public static void switchToProd() { RealmsClient.currentEnvironment = Environment.PRODUCTION; } public static void switchToLocal() { RealmsClient.currentEnvironment = Environment.LOCAL; } public RealmsClient(final String string1, final String string2, final Proxy proxy) { this.sessionId = string1; this.username = string2; RealmsClientConfig.setProxy(proxy); } public RealmsServerList listWorlds() throws RealmsServiceException, IOException { final String string2 = this.url("worlds"); final String string3 = this.execute(Request.get(string2)); return RealmsServerList.parse(string3); } public RealmsServer getOwnWorld(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("worlds" + "/$ID".replace("$ID", String.valueOf(long1))); final String string5 = this.execute(Request.get(string4)); return RealmsServer.parse(string5); } public RealmsServerPlayerLists getLiveStats() throws RealmsServiceException { final String string2 = this.url("activities/liveplayerlist"); final String string3 = this.execute(Request.get(string2)); return RealmsServerPlayerLists.parse(string3); } public RealmsServerAddress join(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("worlds" + "/v1/$ID/join/pc".replace("$ID", "" + long1)); final String string5 = this.execute(Request.get(string4, 5000, 30000)); return RealmsServerAddress.parse(string5); } public void initializeWorld(final long long1, final String string2, final String string3) throws RealmsServiceException, IOException { final RealmsDescriptionDto realmsDescriptionDto6 = new RealmsDescriptionDto(string2, string3); final String string4 = this.url("worlds" + "/$WORLD_ID/initialize".replace("$WORLD_ID", String.valueOf(long1))); final String string5 = RealmsClient.gson.toJson(realmsDescriptionDto6); this.execute(Request.post(string4, string5, 5000, 10000)); } public Boolean mcoEnabled() throws RealmsServiceException, IOException { final String string2 = this.url("mco/available"); final String string3 = this.execute(Request.get(string2)); return Boolean.valueOf(string3); } public Boolean stageAvailable() throws RealmsServiceException, IOException { final String string2 = this.url("mco/stageAvailable"); final String string3 = this.execute(Request.get(string2)); return Boolean.valueOf(string3); } public CompatibleVersionResponse clientCompatible() throws RealmsServiceException, IOException { final String string2 = this.url("mco/client/compatible"); final String string3 = this.execute(Request.get(string2)); CompatibleVersionResponse a4; try { a4 = CompatibleVersionResponse.valueOf(string3); } catch (IllegalArgumentException illegalArgumentException5) { throw new RealmsServiceException(500, "Could not check compatible version, got response: " + string3, -1, ""); } return a4; } public void uninvite(final long long1, final String string) throws RealmsServiceException { final String string2 = this.url("invites" + "/$WORLD_ID/invite/$UUID".replace("$WORLD_ID", String.valueOf(long1)).replace("$UUID", string)); this.execute(Request.delete(string2)); } public void uninviteMyselfFrom(final long long1) throws RealmsServiceException { final String string4 = this.url("invites" + "/$WORLD_ID".replace("$WORLD_ID", String.valueOf(long1))); this.execute(Request.delete(string4)); } public RealmsServer invite(final long long1, final String string) throws RealmsServiceException, IOException { final PlayerInfo playerInfo5 = new PlayerInfo(); playerInfo5.setName(string); final String string2 = this.url("invites" + "/$WORLD_ID".replace("$WORLD_ID", String.valueOf(long1))); final String string3 = this.execute(Request.post(string2, RealmsClient.gson.toJson(playerInfo5))); return RealmsServer.parse(string3); } public BackupList backupsFor(final long long1) throws RealmsServiceException { final String string4 = this.url("worlds" + "/$WORLD_ID/backups".replace("$WORLD_ID", String.valueOf(long1))); final String string5 = this.execute(Request.get(string4)); return BackupList.parse(string5); } public void update(final long long1, final String string2, final String string3) throws RealmsServiceException, UnsupportedEncodingException { final RealmsDescriptionDto realmsDescriptionDto6 = new RealmsDescriptionDto(string2, string3); final String string4 = this.url("worlds" + "/$WORLD_ID".replace("$WORLD_ID", String.valueOf(long1))); this.execute(Request.post(string4, RealmsClient.gson.toJson(realmsDescriptionDto6))); } public void updateSlot(final long long1, final int integer, final RealmsWorldOptions realmsWorldOptions) throws RealmsServiceException, UnsupportedEncodingException { final String string6 = this.url("worlds" + "/$WORLD_ID/slot/$SLOT_ID".replace("$WORLD_ID", String.valueOf(long1)).replace("$SLOT_ID", String.valueOf(integer))); final String string7 = realmsWorldOptions.toJson(); this.execute(Request.post(string6, string7)); } public boolean switchSlot(final long long1, final int integer) throws RealmsServiceException { final String string5 = this.url("worlds" + "/$WORLD_ID/slot/$SLOT_ID".replace("$WORLD_ID", String.valueOf(long1)).replace("$SLOT_ID", String.valueOf(integer))); final String string6 = this.execute(Request.put(string5, "")); return Boolean.valueOf(string6); } public void restoreWorld(final long long1, final String string) throws RealmsServiceException { final String string2 = this.url("worlds" + "/$WORLD_ID/backups".replace("$WORLD_ID", String.valueOf(long1)), "backupId=" + string); this.execute(Request.put(string2, "", 40000, 600000)); } public WorldTemplatePaginatedList fetchWorldTemplates(final int integer1, final int integer2, final RealmsServer.WorldType c) throws RealmsServiceException { final String string5 = this.url("worlds" + "/templates/$WORLD_TYPE".replace("$WORLD_TYPE", c.toString()), String.format("page=%d&pageSize=%d", integer1, integer2)); final String string6 = this.execute(Request.get(string5)); return WorldTemplatePaginatedList.parse(string6); } public Boolean putIntoMinigameMode(final long long1, final String string) throws RealmsServiceException { final String string2 = "/minigames/$MINIGAME_ID/$WORLD_ID".replace("$MINIGAME_ID", string).replace("$WORLD_ID", String.valueOf(long1)); final String string3 = this.url("worlds" + string2); return Boolean.valueOf(this.execute(Request.put(string3, ""))); } public Ops op(final long long1, final String string) throws RealmsServiceException { final String string2 = "/$WORLD_ID/$PROFILE_UUID".replace("$WORLD_ID", String.valueOf(long1)).replace("$PROFILE_UUID", string); final String string3 = this.url("ops" + string2); return Ops.parse(this.execute(Request.post(string3, ""))); } public Ops deop(final long long1, final String string) throws RealmsServiceException { final String string2 = "/$WORLD_ID/$PROFILE_UUID".replace("$WORLD_ID", String.valueOf(long1)).replace("$PROFILE_UUID", string); final String string3 = this.url("ops" + string2); return Ops.parse(this.execute(Request.delete(string3))); } public Boolean open(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("worlds" + "/$WORLD_ID/open".replace("$WORLD_ID", String.valueOf(long1))); final String string5 = this.execute(Request.put(string4, "")); return Boolean.valueOf(string5); } public Boolean close(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("worlds" + "/$WORLD_ID/close".replace("$WORLD_ID", String.valueOf(long1))); final String string5 = this.execute(Request.put(string4, "")); return Boolean.valueOf(string5); } public Boolean resetWorldWithSeed(final long long1, final String string, final Integer integer, final boolean boolean4) throws RealmsServiceException, IOException { final RealmsWorldResetDto realmsWorldResetDto7 = new RealmsWorldResetDto(string, -1L, integer, boolean4); final String string2 = this.url("worlds" + "/$WORLD_ID/reset".replace("$WORLD_ID", String.valueOf(long1))); final String string3 = this.execute(Request.post(string2, RealmsClient.gson.toJson(realmsWorldResetDto7), 30000, 80000)); return Boolean.valueOf(string3); } public Boolean resetWorldWithTemplate(final long long1, final String string) throws RealmsServiceException, IOException { final RealmsWorldResetDto realmsWorldResetDto5 = new RealmsWorldResetDto(null, Long.valueOf(string), -1, false); final String string2 = this.url("worlds" + "/$WORLD_ID/reset".replace("$WORLD_ID", String.valueOf(long1))); final String string3 = this.execute(Request.post(string2, RealmsClient.gson.toJson(realmsWorldResetDto5), 30000, 80000)); return Boolean.valueOf(string3); } public Subscription subscriptionFor(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("subscriptions" + "/$WORLD_ID".replace("$WORLD_ID", String.valueOf(long1))); final String string5 = this.execute(Request.get(string4)); return Subscription.parse(string5); } public int pendingInvitesCount() throws RealmsServiceException { final String string2 = this.url("invites/count/pending"); final String string3 = this.execute(Request.get(string2)); return Integer.parseInt(string3); } public PendingInvitesList pendingInvites() throws RealmsServiceException { final String string2 = this.url("invites/pending"); final String string3 = this.execute(Request.get(string2)); return PendingInvitesList.parse(string3); } public void acceptInvitation(final String string) throws RealmsServiceException { final String string2 = this.url("invites" + "/accept/$INVITATION_ID".replace("$INVITATION_ID", string)); this.execute(Request.put(string2, "")); } public WorldDownload download(final long long1, final int integer) throws RealmsServiceException { final String string5 = this.url("worlds" + "/$WORLD_ID/slot/$SLOT_ID/download".replace("$WORLD_ID", String.valueOf(long1)).replace("$SLOT_ID", String.valueOf(integer))); final String string6 = this.execute(Request.get(string5)); return WorldDownload.parse(string6); } public UploadInfo upload(final long long1, final String string) throws RealmsServiceException { final String string2 = this.url("worlds" + "/$WORLD_ID/backups/upload".replace("$WORLD_ID", String.valueOf(long1))); final UploadInfo uploadInfo6 = new UploadInfo(); if (string != null) { uploadInfo6.setToken(string); } final GsonBuilder gsonBuilder7 = new GsonBuilder(); gsonBuilder7.excludeFieldsWithoutExposeAnnotation(); final Gson gson8 = gsonBuilder7.create(); final String string3 = gson8.toJson(uploadInfo6); return UploadInfo.parse(this.execute(Request.put(string2, string3))); } public void rejectInvitation(final String string) throws RealmsServiceException { final String string2 = this.url("invites" + "/reject/$INVITATION_ID".replace("$INVITATION_ID", string)); this.execute(Request.put(string2, "")); } public void agreeToTos() throws RealmsServiceException { final String string2 = this.url("mco/tos/agreed"); this.execute(Request.post(string2, "")); } public RealmsNews getNews() throws RealmsServiceException, IOException { final String string2 = this.url("mco/v1/news"); final String string3 = this.execute(Request.get(string2, 5000, 10000)); return RealmsNews.parse(string3); } public void sendPingResults(final PingResult pingResult) throws RealmsServiceException { final String string3 = this.url("regions/ping/stat"); this.execute(Request.post(string3, RealmsClient.gson.toJson(pingResult))); } public Boolean trialAvailable() throws RealmsServiceException, IOException { final String string2 = this.url("trial"); final String string3 = this.execute(Request.get(string2)); return Boolean.valueOf(string3); } public void deleteWorld(final long long1) throws RealmsServiceException, IOException { final String string4 = this.url("worlds" + "/$WORLD_ID".replace("$WORLD_ID", String.valueOf(long1))); this.execute(Request.delete(string4)); } private String url(final String string) { return this.url(string, null); } private String url(final String string1, final String string2) { try { final URI uRI4 = new URI(RealmsClient.currentEnvironment.protocol, RealmsClient.currentEnvironment.baseUrl, "/" + string1, string2, null); return uRI4.toASCIIString(); } catch (URISyntaxException uRISyntaxException4) { uRISyntaxException4.printStackTrace(); return null; } } private String execute(final Request czb) throws RealmsServiceException { czb.cookie("sid", this.sessionId); czb.cookie("user", this.username); czb.cookie("version", Realms.getMinecraftVersionString()); try { final int integer3 = czb.responseCode(); if (integer3 == 503) { final int integer4 = czb.getRetryAfterHeader(); throw new RetryCallException(integer4); } final String string4 = czb.text(); if (integer3 >= 200 && integer3 < 300) { return string4; } if (integer3 == 401) { final String string5 = czb.getHeader("WWW-Authenticate"); RealmsClient.LOGGER.info("Could not authorize you against Realms server: " + string5); throw new RealmsServiceException(integer3, string5, -1, string5); } if (string4 == null || string4.length() == 0) { RealmsClient.LOGGER.error("Realms error code: " + integer3 + " message: " + string4); throw new RealmsServiceException(integer3, string4, integer3, ""); } final RealmsError cza5 = new RealmsError(string4); RealmsClient.LOGGER.error("Realms http code: " + integer3 + " - error code: " + cza5.getErrorCode() + " - message: " + cza5.getErrorMessage() + " - raw body: " + string4); throw new RealmsServiceException(integer3, string4, cza5); } catch (RealmsHttpException czf3) { throw new RealmsServiceException(500, "Could not connect to Realms: " + czf3.getMessage(), -1, ""); } } static { RealmsClient.currentEnvironment = Environment.PRODUCTION; LOGGER = LogManager.getLogger(); gson = new Gson(); } public enum Environment { PRODUCTION("pc.realms.minecraft.net", "https"), STAGE("pc-stage.realms.minecraft.net", "https"), LOCAL("localhost:8080", "http"); public String baseUrl; public String protocol; private Environment(final String string3, final String string4) { this.baseUrl = string3; this.protocol = string4; } } public enum CompatibleVersionResponse { COMPATIBLE, OUTDATED, OTHER; } }