Skip to content

Commit

Permalink
v1.1.0
Browse files Browse the repository at this point in the history
  • Loading branch information
Scarsz authored May 24, 2022
2 parents ba8712c + fc5d4d1 commit 49be5ed
Show file tree
Hide file tree
Showing 16 changed files with 390 additions and 58 deletions.
10 changes: 5 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,23 +1,23 @@
# MinecraftAuth/lib
This is a Java library for querying the [minecraftauth.me](https://minecraftauth.me) service.

This project (nor MinecraftAuthentication as a whole) is associated or endorsed by Minecraft/Mojang.
This project (nor MinecraftAuthentication as a whole) is __not__ associated with or endorsed by Minecraft/Mojang.

# Maven [![Latest release](https://img.shields.io/github/release/MinecraftAuthentication/lib.svg)](https://github.com/MinecraftAuthentication/lib/releases/latest)
```xml
<repositories>
<repority>
<repository>
<id>scarsz</id>
<url>https://nexus.scarsz.me/content/groups/public/</url>
</repority>
</repository>
</repositories>
```
```xml
<dependencies>
<dependency>
<groupId>me.minecraftauth</groupId>
<artifactId>lib</artifactId>
<version>LATEST</version>
<version>1.1.0</version>
</dependency>
</dependencies>
```
```
14 changes: 14 additions & 0 deletions deploy.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<settings>
<servers>
<server>
<id>scarsz</id>
<username>${env.NEXUS_USER}</username>
<password>${env.NEXUS_PASS}</password>
</server>
<server>
<id>scarsz-snapshots</id>
<username>${env.NEXUS_USER}</username>
<password>${env.NEXUS_PASS}</password>
</server>
</servers>
</settings>
16 changes: 14 additions & 2 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

<groupId>me.minecraftauth</groupId>
<artifactId>lib</artifactId>
<version>1.0.1</version>
<version>1.1.0</version>

<distributionManagement>
<repository>
Expand Down Expand Up @@ -47,6 +47,17 @@
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
<minimizeJar>true</minimizeJar>

<filters>
<filter>
<artifact>github.scarsz:configuralize</artifact>
<excludes>
<!-- snakeyaml and json simple is already inside craftbukkit -->
<exclude>org/yaml/snakeyaml/**</exclude>
<exclude>org/json/simple/**</exclude>
</excludes>
</filter>
</filters>
</configuration>
</execution>
</executions>
Expand Down Expand Up @@ -88,6 +99,7 @@
<groupId>org.jetbrains</groupId>
<artifactId>annotations</artifactId>
<version>16.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.googlecode.json-simple</groupId>
Expand All @@ -96,4 +108,4 @@
</dependency>
</dependencies>

</project>
</project>
193 changes: 182 additions & 11 deletions src/main/java/me/minecraftauth/lib/AuthService.java
Original file line number Diff line number Diff line change
Expand Up @@ -6,18 +6,39 @@
import me.minecraftauth.lib.account.AccountType;
import me.minecraftauth.lib.account.Identity;
import me.minecraftauth.lib.exception.LookupException;
import me.minecraftauth.lib.account.platform.twitch.SubTier;
import org.json.simple.parser.JSONParser;
import org.json.simple.parser.ParseException;

import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;
import java.util.*;
import java.util.function.Predicate;

public class AuthService {

private static final JSONParser JSON_PARSER = new JSONParser();

// prevent instantiation
private AuthService() {}

private static boolean expectResponseBody(HttpRequest request, Predicate<Dynamic> predicate) throws LookupException {
int status = request.code();
String body = request.body();

if (status / 100 == 2) {
try {
Dynamic response = Dynamic.from(JSON_PARSER.parse(body));
return predicate.test(response);
} catch (HttpRequest.HttpRequestException | ParseException e) {
throw new LookupException("Failed to parse API response", e);
}
} else {
throw new LookupException("MinecraftAuth server returned bad response: " + status + " / " + body);
}
}
private static boolean expectTrue(HttpRequest request) throws LookupException {
return expectResponseBody(request, dynamic -> dynamic.dget("result").convert().intoString().equals("true"));
}

/**
* Look up all of an identifier's linked accounts
* @param from the account type to query by
Expand All @@ -28,23 +49,24 @@ public class AuthService {
public static Optional<Identity> lookup(AccountType from, Object identifier) throws LookupException {
HttpRequest request = HttpRequest.get("https://minecraftauth.me/api/lookup?" + from.name().toLowerCase() + "=" + identifier)
.userAgent("MinecraftAuthLib");
String body = request.body();

if (request.code() >= 200 && request.code() <= 299) {
if (request.code() / 100 == 2) {
try {
Dynamic response = Dynamic.from(JSON_PARSER.parse(request.body()));
Dynamic response = Dynamic.from(JSON_PARSER.parse(body));

Map<AccountType, Account> identifiers = new HashMap<>();
response.children().forEach(dynamic -> Arrays.stream(AccountType.values())
.filter(accountType -> accountType.name().equalsIgnoreCase(dynamic.key().convert().intoString()))
.findFirst().ifPresent(type -> identifiers.put(type, Account.from(type, dynamic.dget("identifier").convert().intoString()))));
return Optional.of(new Identity(identifiers));
} catch (ParseException e) {
} catch (HttpRequest.HttpRequestException | ParseException e) {
throw new LookupException("Failed to parse API response", e);
}
} else if (request.code() == 404) {
return Optional.empty();
} else {
throw new LookupException("MinecraftAuth server returned bad code: " + request.code());
throw new LookupException("MinecraftAuth server returned bad code: " + request.code() + " / " + body);
}
}

Expand All @@ -59,20 +81,169 @@ public static Optional<Identity> lookup(AccountType from, Object identifier) thr
public static Optional<Account> lookup(AccountType from, Object identifier, AccountType to) throws LookupException {
HttpRequest request = HttpRequest.get("https://minecraftauth.me/api/lookup/" + to.name().toLowerCase() + "?" + from.name().toLowerCase() + "=" + identifier)
.userAgent("MinecraftAuthLib");
String body = request.body();

if (request.code() / 100 == 2) {
try {
Dynamic response = Dynamic.from(JSON_PARSER.parse(request.body()));
Dynamic response = Dynamic.from(JSON_PARSER.parse(body));
String id = response.dget(to.name().toLowerCase() + ".identifier").convert().intoString();
return Optional.of(Account.from(to, id));
} catch (ParseException e) {
} catch (HttpRequest.HttpRequestException | ParseException e) {
throw new LookupException("Failed to parse API response", e);
}
} else if (request.code() == 404) {
return Optional.empty();
} else {
throw new LookupException("MinecraftAuth server returned bad code: " + request.code());
throw new LookupException("MinecraftAuth server returned bad response: " + request.code() + " / " + body);
}
}

private static boolean isFollowing(String serverToken, AccountType platform, UUID minecraftUuid) throws LookupException {
HttpRequest request = HttpRequest.get("https://minecraftauth.me/api/following?platform=" + platform.name().toLowerCase() + "&minecraft=" + minecraftUuid)
.userAgent("MinecraftAuthLib")
.authorization("Basic " + serverToken);
return expectTrue(request);
}

private static boolean isSubscribed(String serverToken, AccountType platform, UUID minecraftUuid, Object data) throws LookupException {
HttpRequest request = HttpRequest.get("https://minecraftauth.me/api/subscribed?platform=" + platform.name().toLowerCase() + "&minecraft=" + minecraftUuid + (data != null ? "&data=" + data : ""))
.userAgent("MinecraftAuthLib")
.authorization("Basic " + serverToken);
return expectTrue(request);
}

/**
* Query if the given Discord user ID is in the given Discord server
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param serverId the Discord server ID to query
* @return if the given Discord user (and the Minecraft Authentication bot) is in the given server
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isDiscordMemberPresent(String serverToken, UUID minecraftUuid, String serverId) throws LookupException {
HttpRequest request = HttpRequest.get("https://minecraftauth.me/api/discord/present?minecraft=" + minecraftUuid + "&server=" + serverId)
.userAgent("MinecraftAuthLib")
.authorization("Basic " + serverToken);
return expectTrue(request);
}
/**
* Query if the given Discord user ID has the given Discord role
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param roleId the Discord role ID to query
* @return if the given Discord user has the given role
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isDiscordRolePresent(String serverToken, UUID minecraftUuid, String roleId) throws LookupException {
return isSubscribed(serverToken, AccountType.DISCORD, minecraftUuid, roleId);
}

/**
* Query if the given Patreon uid is a patron of the server token's Patreon campaign
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the given Patreon uid is a patron of the server token's Patreon campaign
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedPatreon(String serverToken, UUID minecraftUuid) throws LookupException {
return isSubscribed(serverToken, AccountType.PATREON, minecraftUuid, null);
}
/**
* Query if the given Patreon uid is a patron of the server token's Patreon campaign
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param tierTitle the title of the requested Patreon tier
* @return if the given Patreon uid is a patron of the server token's Patreon campaign
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedPatreon(String serverToken, UUID minecraftUuid, String tierTitle) throws LookupException {
return isSubscribed(serverToken, AccountType.PATREON, minecraftUuid, tierTitle);
}

/**
* Query if the given Glimpse user is a sponsor of the server token's Glimpse user
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the given Glimpse user is a sponsor of the server token's Glimpse user
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedGlimpse(String serverToken, UUID minecraftUuid) throws LookupException {
return isSubscribed(serverToken, AccountType.GLIMPSE, minecraftUuid, null);
}
/**
* Query if the given Glimpse user is a sponsor of the server token's Glimpse user
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param levelName the name of the requested Glimpse level
* @return if the given Glimpse user is a sponsor of the server token's Glimpse user
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedGlimpse(String serverToken, UUID minecraftUuid, String levelName) throws LookupException {
return isSubscribed(serverToken, AccountType.GLIMPSE, minecraftUuid, levelName);
}

/**
* Query if the given Twitch uid is following the server token's Twitch channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the given Twitch uid is following the server token's Twitch channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isFollowingTwitch(String serverToken, UUID minecraftUuid) throws LookupException {
return isFollowing(serverToken, AccountType.TWITCH, minecraftUuid);
}
/**
* Query if the given Twitch uid is subbed to the server token's Twitch channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the given Twitch uid is subbed to the server token's Twitch channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedTwitch(String serverToken, UUID minecraftUuid) throws LookupException {
return isSubscribed(serverToken, AccountType.TWITCH, minecraftUuid, null);
}
/**
* Query if the given Twitch uid is subbed to the server token's Twitch channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param tier the required tier level to qualify as being subscribed
* @return if the given Twitch uid is subbed to the server token's Twitch channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedTwitch(String serverToken, UUID minecraftUuid, SubTier tier) throws LookupException {
return isSubscribed(serverToken, AccountType.TWITCH, minecraftUuid, tier.getValue());
}

/**
* Query if the player's YouTube account is subscribed to the server token's YouTube channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the player's YouTube account is subscribed to the server token's YouTube channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isSubscribedYouTube(String serverToken, UUID minecraftUuid) throws LookupException {
return isFollowing(serverToken, AccountType.GOOGLE, minecraftUuid);
}
/**
* Query if the player's YouTube account is a paid member of the server token's YouTube channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @return if the player's YouTube account is a paid member of the server token's YouTube channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isMemberYouTube(String serverToken, UUID minecraftUuid) throws LookupException {
return isSubscribed(serverToken, AccountType.GOOGLE, minecraftUuid, null);
}
/**
* Query if the player's YouTube account is a paid member of the server token's YouTube channel
* @param serverToken the server authentication token to query data for
* @param minecraftUuid the Minecraft player UUID to query
* @param tier the required tier level to qualify as being a member
* @return if the player's YouTube account is a paid member of the server token's YouTube channel
* @throws LookupException if the API returns abnormal error code
*/
public static boolean isMemberYouTube(String serverToken, UUID minecraftUuid, String tier) throws LookupException {
return isSubscribed(serverToken, AccountType.GOOGLE, minecraftUuid, tier);
}

}
10 changes: 10 additions & 0 deletions src/main/java/me/minecraftauth/lib/account/Account.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
package me.minecraftauth.lib.account;

import me.minecraftauth.lib.AuthService;
import me.minecraftauth.lib.account.platform.discord.DiscordAccount;
import me.minecraftauth.lib.account.platform.glimpse.GlimpseAccount;
import me.minecraftauth.lib.account.platform.google.GoogleAccount;
import me.minecraftauth.lib.account.platform.minecraft.MinecraftAccount;
import me.minecraftauth.lib.account.platform.patreon.PatreonAccount;
import me.minecraftauth.lib.account.platform.twitch.TwitchAccount;
import me.minecraftauth.lib.exception.LookupException;

import java.util.Optional;
Expand All @@ -18,6 +24,10 @@ public static <T extends Account> T from(AccountType type, String identifier) {
return (T) new MinecraftAccount(UUID.fromString(identifier));
case PATREON:
return (T) new PatreonAccount(Integer.parseInt(identifier));
case GLIMPSE:
return (T) new GlimpseAccount(identifier);
case GOOGLE:
return (T) new GoogleAccount(identifier);
case TWITCH:
return (T) new TwitchAccount(Integer.parseInt(identifier));
default:
Expand Down
4 changes: 3 additions & 1 deletion src/main/java/me/minecraftauth/lib/account/AccountType.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ public enum AccountType {
DISCORD,
MINECRAFT,
PATREON,
TWITCH;
TWITCH,
GLIMPSE,
GOOGLE;

@Override
public String toString() {
Expand Down
Loading

0 comments on commit 49be5ed

Please sign in to comment.