/plan unregister command

- Fixed tests and other queries not using new web user format.
This commit is contained in:
Risto Lahtela 2020-05-04 11:16:07 +03:00
parent ea2ae5d3e1
commit 5570a2b938
26 changed files with 368 additions and 146 deletions

View File

@ -51,6 +51,7 @@ public class PlanCommand extends TreeCmdNode {
private final ListServersCommand listServersCommand;
private final Lazy<WebUserCommand> webUserCommand;
private final RegisterCommand registerCommand;
private final UnregisterCommand unregisterCommand;
private final InfoCommand infoCommand;
private final ReloadCommand reloadCommand;
private final Lazy<ManageCommand> manageCommand;
@ -74,6 +75,7 @@ public class PlanCommand extends TreeCmdNode {
// Group 2
Lazy<WebUserCommand> webUserCommand,
RegisterCommand registerCommand,
UnregisterCommand unregisterCommand,
// Group 3
InfoCommand infoCommand,
ReloadCommand reloadCommand,
@ -81,6 +83,7 @@ public class PlanCommand extends TreeCmdNode {
DevCommand devCommand
) {
super("plan", "", CommandType.CONSOLE, null);
this.unregisterCommand = unregisterCommand;
commandsRegistered = false;
@ -121,7 +124,8 @@ public class PlanCommand extends TreeCmdNode {
};
CommandNode[] webGroup = {
webUserCommand.get(),
registerCommand
registerCommand,
unregisterCommand
};
CommandNode[] manageGroup = {
infoCommand,

View File

@ -46,6 +46,7 @@ public class PlanProxyCommand extends TreeCmdNode {
private final ListServersCommand listServersCommand;
private final ListPlayersCommand listPlayersCommand;
private final RegisterCommand registerCommand;
private final UnregisterCommand unregisterCommand;
private final Lazy<WebUserCommand> webUserCommand;
private final ManageRawDataCommand rawDataCommand;
private final ReloadCommand reloadCommand;
@ -65,6 +66,7 @@ public class PlanProxyCommand extends TreeCmdNode {
ListPlayersCommand listPlayersCommand,
// Group 2
RegisterCommand registerCommand,
UnregisterCommand unregisterCommand,
Lazy<WebUserCommand> webUserCommand,
// Group 3
ManageRawDataCommand rawDataCommand,
@ -73,6 +75,7 @@ public class PlanProxyCommand extends TreeCmdNode {
DisableCommand disableCommand
) {
super(mainCommandName, Permissions.MANAGE.getPermission(), CommandType.CONSOLE, null);
this.unregisterCommand = unregisterCommand;
this.uninstalledCommand = uninstalledCommand;
commandsRegistered = false;
@ -103,6 +106,7 @@ public class PlanProxyCommand extends TreeCmdNode {
};
CommandNode[] webGroup = {
registerCommand,
unregisterCommand,
webUserCommand.get()
};
CommandNode[] manageGroup = {

View File

@ -134,7 +134,7 @@ public class AnalyzeCommand extends CommandNode {
private void sendWebUserNotificationIfNecessary(Sender sender) {
if (webServer.isAuthRequired() &&
CommandUtils.isPlayer(sender) &&
!dbSystem.getDatabase().query(WebUserQueries.fetchWebUser(sender.getName())).isPresent()) {
!dbSystem.getDatabase().query(WebUserQueries.fetchUserLinkedTo(sender.getName())).isPresent()) {
sender.sendMessage("§e" + locale.getString(CommandLang.NO_WEB_USER_NOTIFY));
}
}

View File

@ -124,7 +124,7 @@ public class InspectCommand extends CommandNode {
private void checkWebUserAndNotify(Sender sender) {
if (CommandUtils.isPlayer(sender) && webServer.isAuthRequired()) {
boolean senderHasWebUser = dbSystem.getDatabase().query(WebUserQueries.fetchWebUser(sender.getName())).isPresent();
boolean senderHasWebUser = dbSystem.getDatabase().query(WebUserQueries.fetchUserLinkedTo(sender.getName())).isPresent();
if (!senderHasWebUser) {
sender.sendMessage("§e" + locale.getString(CommandLang.NO_WEB_USER_NOTIFY));

View File

@ -161,11 +161,11 @@ public class RegisterCommand extends CommandNode {
String playerName = sender.getName();
UUID linkedToUUID = uuidUtility.getUUIDOf(playerName);
String username = arguments.get(1).orElse(playerName);
registerUser(new User(username, playerName, linkedToUUID, passwordHash, Collections.emptyList()), sender, permissionLevel);
registerUser(new User(username, playerName, linkedToUUID, passwordHash, permissionLevel, Collections.emptyList()), sender, permissionLevel);
} else {
String username = arguments.get(1)
.orElseThrow(() -> new IllegalArgumentException(notEnoughArgsMsg));
registerUser(new User(username, "console", null, passwordHash, Collections.emptyList()), sender, permissionLevel);
registerUser(new User(username, "console", null, passwordHash, permissionLevel, Collections.emptyList()), sender, permissionLevel);
}
}
@ -188,6 +188,7 @@ public class RegisterCommand extends CommandNode {
private void registerUser(User user, Sender sender, int permissionLevel) {
processing.submitCritical(() -> {
String username = user.getUsername();
user.setPermissionLevel(permissionLevel);
try {
Database database = dbSystem.getDatabase();
boolean userExists = database.query(WebUserQueries.fetchUser(username)).isPresent();
@ -195,7 +196,7 @@ public class RegisterCommand extends CommandNode {
sender.sendMessage(locale.getString(CommandLang.FAIL_WEB_USER_EXISTS));
return;
}
database.executeTransaction(new RegisterWebUserTransaction(user, permissionLevel))
database.executeTransaction(new RegisterWebUserTransaction(user))
.get(); // Wait for completion
sender.sendMessage(locale.getString(CommandLang.WEB_USER_REGISTER_SUCCESS, username));

View File

@ -0,0 +1,134 @@
/*
* This file is part of Player Analytics (Plan).
*
* Plan is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License v3 as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Plan is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Plan. If not, see <https://www.gnu.org/licenses/>.
*/
package com.djrapitops.plan.commands.subcommands;
import com.djrapitops.plan.commands.Arguments;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.delivery.webserver.auth.FailReason;
import com.djrapitops.plan.identification.UUIDUtility;
import com.djrapitops.plan.processing.Processing;
import com.djrapitops.plan.settings.Permissions;
import com.djrapitops.plan.settings.locale.Locale;
import com.djrapitops.plan.settings.locale.lang.CmdHelpLang;
import com.djrapitops.plan.settings.locale.lang.CommandLang;
import com.djrapitops.plan.settings.locale.lang.ManageLang;
import com.djrapitops.plan.storage.database.DBSystem;
import com.djrapitops.plan.storage.database.Database;
import com.djrapitops.plan.storage.database.queries.objects.WebUserQueries;
import com.djrapitops.plan.storage.database.transactions.commands.RemoveWebUserTransaction;
import com.djrapitops.plugin.command.CommandNode;
import com.djrapitops.plugin.command.CommandType;
import com.djrapitops.plugin.command.CommandUtils;
import com.djrapitops.plugin.command.Sender;
import com.djrapitops.plugin.logging.L;
import com.djrapitops.plugin.logging.error.ErrorHandler;
import javax.inject.Inject;
import javax.inject.Singleton;
import java.util.Arrays;
import java.util.Objects;
import java.util.Optional;
import java.util.UUID;
/**
* Subcommand for deleting a WebUser.
*
* @author Rsl1122
*/
@Singleton
public class UnregisterCommand extends CommandNode {
private final Locale locale;
private final Processing processing;
private final DBSystem dbSystem;
private final UUIDUtility uuidUtility;
private final ErrorHandler errorHandler;
@Inject
public UnregisterCommand(
Locale locale,
Processing processing,
DBSystem dbSystem,
UUIDUtility uuidUtility,
ErrorHandler errorHandler
) {
super("unregister", "", CommandType.PLAYER_OR_ARGS);
this.locale = locale;
this.processing = processing;
this.dbSystem = dbSystem;
this.uuidUtility = uuidUtility;
this.errorHandler = errorHandler;
setShortHelp(locale.getString(CmdHelpLang.WEB_DELETE));
setArguments("[username]");
}
@Override
public void onCommand(Sender sender, String commandLabel, String[] args) {
Database.State dbState = dbSystem.getDatabase().getState();
if (dbState != Database.State.OPEN) {
sender.sendMessage(locale.getString(CommandLang.FAIL_DATABASE_NOT_OPEN, dbState.name()));
return;
}
Arguments arguments = new Arguments(args);
Optional<String> givenUsername = arguments.get(0);
processing.submitNonCritical(() -> {
Database database = dbSystem.getDatabase();
try {
UUID playerUUID = CommandUtils.isPlayer(sender) ? uuidUtility.getUUIDOf(sender.getName()) : null;
String username;
if (!givenUsername.isPresent() && playerUUID != null) {
Optional<User> found = database.query(WebUserQueries.fetchUser(playerUUID));
if (!found.isPresent()) {
sender.sendMessage("§c" + locale.getString(FailReason.USER_DOES_NOT_EXIST));
return;
}
username = found.get().getUsername();
} else if (!givenUsername.isPresent()) {
sender.sendMessage("§c" + locale.getString(CommandLang.FAIL_REQ_ONE_ARG, Arrays.toString(this.getArguments())));
return;
} else {
username = givenUsername.get();
}
Optional<User> found = database.query(WebUserQueries.fetchUser(username));
if (!found.isPresent()) {
sender.sendMessage("§c" + locale.getString(FailReason.USER_DOES_NOT_EXIST));
return;
}
User presentUser = found.get();
if (!Objects.equals(playerUUID, presentUser.getLinkedToUUID()) && sender.hasPermission(Permissions.MANAGE_WEB.getPerm())) {
sender.sendMessage("§c" + locale.getString(CommandLang.USER_NOT_LINKED));
return;
}
sender.sendMessage(locale.getString(ManageLang.PROGRESS_START));
database.executeTransaction(new RemoveWebUserTransaction(username))
.get(); // Wait for completion
sender.sendMessage(locale.getString(ManageLang.PROGRESS_SUCCESS));
} catch (Exception e) {
errorHandler.log(L.ERROR, this.getClass(), e);
sender.sendMessage(locale.getString(ManageLang.PROGRESS_FAIL, e.getMessage()));
}
});
}
}

View File

@ -16,7 +16,7 @@
*/
package com.djrapitops.plan.commands.subcommands.webuser;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.processing.Processing;
import com.djrapitops.plan.settings.Permissions;
import com.djrapitops.plan.settings.locale.Locale;
@ -85,13 +85,13 @@ public class WebCheckCommand extends CommandNode {
processing.submitNonCritical(() -> {
try {
Database db = dbSystem.getDatabase();
Optional<WebUser> found = db.query(WebUserQueries.fetchWebUser(user));
Optional<User> found = db.query(WebUserQueries.fetchUser(user));
if (!found.isPresent()) {
sender.sendMessage(locale.getString(CommandLang.FAIL_WEB_USER_NOT_EXISTS));
return;
}
WebUser info = found.get();
sender.sendMessage(locale.getString(CommandLang.WEB_USER_LIST, info.getName(), info.getPermLevel()));
User info = found.get();
sender.sendMessage(locale.getString(CommandLang.WEB_USER_LIST, info.getUsername(), info.getPermissionLevel()));
} catch (Exception e) {
errorHandler.log(L.ERROR, this.getClass(), e);
sender.sendMessage(locale.getString(ManageLang.PROGRESS_FAIL, e.getMessage()));

View File

@ -16,7 +16,8 @@
*/
package com.djrapitops.plan.commands.subcommands.webuser;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.delivery.webserver.auth.FailReason;
import com.djrapitops.plan.processing.Processing;
import com.djrapitops.plan.settings.Permissions;
import com.djrapitops.plan.settings.locale.Locale;
@ -86,9 +87,9 @@ public class WebDeleteCommand extends CommandNode {
processing.submitNonCritical(() -> {
try {
Database db = dbSystem.getDatabase();
Optional<WebUser> found = db.query(WebUserQueries.fetchWebUser(user));
Optional<User> found = db.query(WebUserQueries.fetchUser(user));
if (!found.isPresent()) {
sender.sendMessage("§c[Plan] User Doesn't exist.");
sender.sendMessage("§c" + locale.getString(FailReason.USER_DOES_NOT_EXIST));
return;
}
sender.sendMessage(locale.getString(ManageLang.PROGRESS_START));

View File

@ -16,7 +16,7 @@
*/
package com.djrapitops.plan.commands.subcommands.webuser;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.processing.Processing;
import com.djrapitops.plan.settings.Permissions;
import com.djrapitops.plan.settings.locale.Locale;
@ -76,10 +76,10 @@ public class WebListUsersCommand extends CommandNode {
processing.submitNonCritical(() -> {
try {
List<WebUser> users = dbSystem.getDatabase().query(WebUserQueries.fetchAllPlanWebUsers());
List<User> users = dbSystem.getDatabase().query(WebUserQueries.fetchAllUsers());
sender.sendMessage(locale.getString(CommandLang.HEADER_WEB_USERS, users.size()));
for (WebUser user : users) {
sender.sendMessage(locale.getString(CommandLang.WEB_USER_LIST, user.getName(), user.getPermLevel()));
for (User user : users) {
sender.sendMessage(locale.getString(CommandLang.WEB_USER_LIST, user.getUsername(), user.getPermissionLevel()));
}
sender.sendMessage(">");
} catch (Exception e) {

View File

@ -20,6 +20,7 @@ import com.djrapitops.plan.delivery.web.resolver.request.WebUser;
import com.djrapitops.plan.utilities.PassEncryptUtil;
import java.util.Collection;
import java.util.Objects;
import java.util.UUID;
/**
@ -33,13 +34,15 @@ public class User {
private final String linkedTo;
private final UUID linkedToUUID; // null for 'console'
private final String passwordHash;
private int permissionLevel;
private final Collection<String> permissions;
public User(String username, String linkedTo, UUID linkedToUUID, String passwordHash, Collection<String> permissions) {
public User(String username, String linkedTo, UUID linkedToUUID, String passwordHash, int permissionLevel, Collection<String> permissions) {
this.username = username;
this.linkedTo = linkedTo;
this.linkedToUUID = linkedToUUID;
this.passwordHash = passwordHash;
this.permissionLevel = permissionLevel;
this.permissions = permissions;
}
@ -66,4 +69,44 @@ public class User {
public String getPasswordHash() {
return passwordHash;
}
@Deprecated
public int getPermissionLevel() {
return permissionLevel;
}
@Deprecated
public void setPermissionLevel(int permissionLevel) {
this.permissionLevel = permissionLevel;
}
@Override
public String toString() {
return "User{" +
"username='" + username + '\'' +
", linkedTo='" + linkedTo + '\'' +
", linkedToUUID=" + linkedToUUID +
", passwordHash='" + passwordHash + '\'' +
", permissionLevel=" + permissionLevel +
", permissions=" + permissions +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
User user = (User) o;
return permissionLevel == user.permissionLevel &&
Objects.equals(username, user.username) &&
Objects.equals(linkedTo, user.linkedTo) &&
Objects.equals(linkedToUUID, user.linkedToUUID) &&
Objects.equals(passwordHash, user.passwordHash) &&
Objects.equals(permissions, user.permissions);
}
@Override
public int hashCode() {
return Objects.hash(username, linkedTo, linkedToUUID, passwordHash, permissionLevel, permissions);
}
}

View File

@ -59,7 +59,7 @@ public class RegistrationBin {
}
public User toUser(UUID linkedToUUID) {
return new User(username, null, linkedToUUID, passwordHash, Collections.emptyList());
return new User(username, null, linkedToUUID, passwordHash, 100, Collections.emptyList());
}
}
}

View File

@ -50,7 +50,7 @@ public enum CmdHelpLang implements Lang {
WEB_LEVEL("Command Help - /plan web level", "Information about permission levels"),
WEB_LIST("Command Help - /plan web list", "List Web Users"),
WEB_CHECK("Command Help - /plan web check", "Inspect a Web User"),
WEB_DELETE("Command Help - /plan web delete", "Delete a Web User"),
WEB_DELETE("Command Help - /plan web delete", "Unregister a Web User"),
MANAGE_RAW_DATA("Command Help - /plan manage raw", "View raw JSON of player data"),
MANAGE_UNINSTALLED("Command Help - /plan manage uninstalled", "Mark a server as uninstalled in the database.");

View File

@ -29,6 +29,7 @@ public enum CommandLang implements Lang {
FAIL_USERNAME_NOT_KNOWN("Cmd FAIL - Unknown Username", "§cUser has not been seen on this server"),
FAIL_DATABASE_NOT_OPEN("Cmd FAIL - Database not open", "§cDatabase is ${0} - Please try again a bit later."),
WARN_DATABASE_NOT_OPEN("Cmd WARN - Database not open", "§eDatabase is ${0} - This might take longer than expected.."),
USER_NOT_LINKED("Cmd FAIL - Users not linked", "User is not linked to your account and you don't have permission to remove other user's accounts."),
FAIL_WEB_USER_EXISTS("Cmd FAIL - WebUser exists", "§cUser already exists!"),
FAIL_WEB_USER_NOT_EXISTS("Cmd FAIL - WebUser does not exists", "§cUser does not exists!"),

View File

@ -40,7 +40,8 @@ public enum ManageLang implements Lang {
FAIL_IMPORTER_NOT_FOUND("Manage - Fail No Importer", "§eImporter '${0}' doesn't exist"),
FAIL_EXPORTER_NOT_FOUND("Manage - Fail No Exporter", "§eExporter '${0}' doesn't exist"),
NO_SERVER("Manage - Fail No Server", "No server found with given parameters."),
UNINSTALLING_SAME_SERVER("Manage - Fail Same server", "Can not mark this server as uninstalled (You are on it)");
UNINSTALLING_SAME_SERVER("Manage - Fail Same server", "Can not mark this server as uninstalled (You are on it)"),
;
private final String identifier;
private final String defaultValue;

View File

@ -17,7 +17,7 @@
package com.djrapitops.plan.storage.database.queries;
import com.djrapitops.plan.delivery.domain.Nickname;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.delivery.domain.keys.SessionKeys;
import com.djrapitops.plan.gathering.domain.*;
import com.djrapitops.plan.identification.Server;
@ -29,6 +29,7 @@ import org.apache.commons.lang3.StringUtils;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Types;
import java.util.Collection;
import java.util.List;
import java.util.Map;
@ -113,13 +114,7 @@ public class LargeStoreQueries {
};
}
/**
* Execute a big batch of web user insert statements.
*
* @param users Collection of Plan WebUsers.
* @return Executable, use inside a {@link com.djrapitops.plan.storage.database.transactions.Transaction}
*/
public static Executable storeAllPlanWebUsers(Collection<WebUser> users) {
public static Executable storeAllPlanWebUsers(Collection<User> users) {
if (Verify.isEmpty(users)) {
return Executable.empty();
}
@ -127,14 +122,15 @@ public class LargeStoreQueries {
return new ExecBatchStatement(SecurityTable.INSERT_STATEMENT) {
@Override
public void prepare(PreparedStatement statement) throws SQLException {
for (WebUser user : users) {
String userName = user.getName();
String pass = user.getSaltedPassHash();
int permLvl = user.getPermLevel();
statement.setString(1, userName);
statement.setString(2, pass);
statement.setInt(3, permLvl);
for (User user : users) {
statement.setString(1, user.getUsername());
if (user.getLinkedToUUID() == null) {
statement.setNull(2, Types.VARCHAR);
} else {
statement.setString(2, user.getLinkedToUUID().toString());
}
statement.setString(3, user.getPasswordHash());
statement.setInt(4, user.getPermissionLevel());
statement.addBatch();
}
}

View File

@ -27,6 +27,7 @@ import com.djrapitops.plan.storage.database.sql.tables.UsersTable;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Types;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
@ -45,31 +46,6 @@ public class WebUserQueries {
/* Static method class */
}
/**
* Query database for all Plan WebUsers.
*
* @return List of Plan WebUsers.
*/
@Deprecated
public static Query<List<WebUser>> fetchAllPlanWebUsers() {
String sql = SELECT + '*' + FROM + SecurityTable.TABLE_NAME + ORDER_BY + SecurityTable.PERMISSION_LEVEL + " ASC";
return new QueryAllStatement<List<WebUser>>(sql, 5000) {
@Override
public List<WebUser> processResults(ResultSet set) throws SQLException {
List<WebUser> list = new ArrayList<>();
while (set.next()) {
String user = set.getString(SecurityTable.USERNAME);
String saltedPassHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
int permissionLevel = set.getInt(SecurityTable.PERMISSION_LEVEL);
WebUser info = new WebUser(user, saltedPassHash, permissionLevel);
list.add(info);
}
return list;
}
};
}
public static Query<Optional<User>> fetchUser(String username) {
String sql = SELECT + '*' + FROM + SecurityTable.TABLE_NAME +
LEFT_JOIN + UsersTable.TABLE_NAME + " on " + SecurityTable.LINKED_TO + "=" + UsersTable.USER_UUID +
@ -86,33 +62,88 @@ public class WebUserQueries {
String linkedTo = set.getString(UsersTable.USER_NAME);
UUID linkedToUUID = linkedTo != null ? UUID.fromString(set.getString(SecurityTable.LINKED_TO)) : null;
String passwordHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
List<String> permissions = WebUser.getPermissionsForLevel(set.getInt(SecurityTable.PERMISSION_LEVEL));
return Optional.of(new User(username, linkedTo != null ? linkedTo : "console", linkedToUUID, passwordHash, permissions));
int permissionLevel = set.getInt(SecurityTable.PERMISSION_LEVEL);
List<String> permissions = WebUser.getPermissionsForLevel(permissionLevel);
return Optional.of(new User(username, linkedTo != null ? linkedTo : "console", linkedToUUID, passwordHash, permissionLevel, permissions));
}
return Optional.empty();
}
};
}
@Deprecated
public static Query<Optional<WebUser>> fetchWebUser(String called) {
public static Query<Optional<User>> fetchUserLinkedTo(String playerName) {
String sql = SELECT + '*' + FROM + SecurityTable.TABLE_NAME +
WHERE + SecurityTable.USERNAME + "=? LIMIT 1";
return new QueryStatement<Optional<WebUser>>(sql) {
LEFT_JOIN + UsersTable.TABLE_NAME + " on " + SecurityTable.LINKED_TO + "=" + UsersTable.USER_UUID +
WHERE + UsersTable.USER_NAME + "=? LIMIT 1";
return new QueryStatement<Optional<User>>(sql) {
@Override
public void prepare(PreparedStatement statement) throws SQLException {
statement.setString(1, called);
statement.setString(1, playerName);
}
@Override
public Optional<WebUser> processResults(ResultSet set) throws SQLException {
public Optional<User> processResults(ResultSet set) throws SQLException {
if (set.next()) {
String saltedPassHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
String linkedTo = set.getString(UsersTable.USER_NAME);
UUID linkedToUUID = linkedTo != null ? UUID.fromString(set.getString(SecurityTable.LINKED_TO)) : null;
String passwordHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
int permissionLevel = set.getInt(SecurityTable.PERMISSION_LEVEL);
return Optional.of(new WebUser(called, saltedPassHash, permissionLevel));
List<String> permissions = WebUser.getPermissionsForLevel(permissionLevel);
return Optional.of(new User(playerName, linkedTo != null ? linkedTo : "console", linkedToUUID, passwordHash, permissionLevel, permissions));
}
return Optional.empty();
}
};
}
public static Query<Optional<User>> fetchUser(UUID linkedToUUID) {
String sql = SELECT + '*' + FROM + SecurityTable.TABLE_NAME +
LEFT_JOIN + UsersTable.TABLE_NAME + " on " + SecurityTable.LINKED_TO + "=" + UsersTable.USER_UUID +
WHERE + SecurityTable.LINKED_TO + "=? LIMIT 1";
return new QueryStatement<Optional<User>>(sql) {
@Override
public void prepare(PreparedStatement statement) throws SQLException {
if (linkedToUUID == null) {
statement.setNull(1, Types.VARCHAR);
} else {
statement.setString(1, linkedToUUID.toString());
}
}
@Override
public Optional<User> processResults(ResultSet set) throws SQLException {
if (set.next()) {
String username = set.getString(SecurityTable.USERNAME);
String linkedTo = set.getString(UsersTable.USER_NAME);
String passwordHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
int permissionLevel = set.getInt(SecurityTable.PERMISSION_LEVEL);
List<String> permissions = WebUser.getPermissionsForLevel(permissionLevel);
return Optional.of(new User(username, linkedTo != null ? linkedTo : "console", linkedToUUID, passwordHash, permissionLevel, permissions));
}
return Optional.empty();
}
};
}
public static Query<List<User>> fetchAllUsers() {
String sql = SELECT + '*' + FROM + SecurityTable.TABLE_NAME +
LEFT_JOIN + UsersTable.TABLE_NAME + " on " + SecurityTable.LINKED_TO + "=" + UsersTable.USER_UUID;
return new QueryAllStatement<List<User>>(sql) {
@Override
public List<User> processResults(ResultSet set) throws SQLException {
List<User> users = new ArrayList<>();
while (set.next()) {
String username = set.getString(SecurityTable.USERNAME);
String linkedTo = set.getString(UsersTable.USER_NAME);
UUID linkedToUUID = linkedTo != null ? UUID.fromString(set.getString(SecurityTable.LINKED_TO)) : null;
String passwordHash = set.getString(SecurityTable.SALT_PASSWORD_HASH);
int permissionLevel = set.getInt(SecurityTable.PERMISSION_LEVEL);
List<String> permissions = WebUser.getPermissionsForLevel(permissionLevel);
users.add(new User(username, linkedTo != null ? linkedTo : "console", linkedToUUID, passwordHash, permissionLevel, permissions));
}
return users;
}
};
}
}

View File

@ -47,7 +47,7 @@ public class SecurityTable {
public static String createTableSQL(DBType dbType) {
return CreateTableBuilder.create(TABLE_NAME, dbType)
.column(USERNAME, Sql.varchar(100)).notNull().unique()
.column(LINKED_TO, Sql.varchar(36))
.column(LINKED_TO, Sql.varchar(36)).defaultValue("''")
.column(SALT_PASSWORD_HASH, Sql.varchar(100)).notNull().unique()
.column(PERMISSION_LEVEL, Sql.INT).notNull()
.toString();

View File

@ -80,7 +80,7 @@ public class BackupCopyTransaction extends RemoveEverythingTransaction {
}
private void copyPlanWebUsers() {
copy(LargeStoreQueries::storeAllPlanWebUsers, WebUserQueries.fetchAllPlanWebUsers());
copy(LargeStoreQueries::storeAllPlanWebUsers, WebUserQueries.fetchAllUsers());
}
private void copyPlanServerInformation() {

View File

@ -33,11 +33,9 @@ import java.sql.Types;
public class RegisterWebUserTransaction extends Transaction {
private final User user;
private final int permissionLevel;
public RegisterWebUserTransaction(User user, int permissionLevel) {
public RegisterWebUserTransaction(User user) {
this.user = user;
this.permissionLevel = permissionLevel;
}
@Override
@ -52,7 +50,7 @@ public class RegisterWebUserTransaction extends Transaction {
statement.setString(2, user.getLinkedToUUID().toString());
}
statement.setString(3, user.getPasswordHash());
statement.setInt(4, permissionLevel);
statement.setInt(4, user.getPermissionLevel());
}
});
}

View File

@ -20,12 +20,15 @@ import com.djrapitops.plan.delivery.web.resolver.exception.BadRequestException;
import com.djrapitops.plan.delivery.web.resolver.exception.NotFoundException;
import com.djrapitops.plan.exceptions.connection.ForbiddenException;
import com.djrapitops.plan.exceptions.connection.WebException;
import com.djrapitops.plan.utilities.Base64Util;
import org.apache.commons.compress.utils.IOUtils;
import org.junit.jupiter.api.Test;
import utilities.HTTPConnector;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import static org.junit.jupiter.api.Assertions.assertTrue;
@ -50,28 +53,53 @@ interface HttpsServerTest {
webServerIsRunningHTTPS();
String address = "https://localhost:" + testPortNumber();
URL url = new URL(address);
HttpURLConnection connection = connector.getConnection("GET", address);
String user = Base64Util.encode("test:testPass");
connection.setRequestProperty("Authorization", "Basic " + user);
String cookie = login(address);
testAccess(address, cookie);
}
int responseCode = connection.getResponseCode();
default void testAccess(String address, String cookie) throws IOException, KeyManagementException, NoSuchAlgorithmException {
HttpURLConnection connection = null;
try {
connection = connector.getConnection("GET", address);
connection.setRequestProperty("Cookie", cookie);
switch (responseCode) {
case 200:
case 302:
return;
case 400:
throw new BadRequestException("Bad Request: " + url.toString());
case 403:
throw new ForbiddenException(url.toString() + " returned 403");
case 404:
throw new NotFoundException(url.toString() + " returned a 404, ensure that your server is connected to an up to date Plan server.");
case 500:
throw new IllegalStateException(); // Not supported
default:
throw new WebException(url.toString() + "| Wrong response code " + responseCode);
int responseCode = connection.getResponseCode();
switch (responseCode) {
case 200:
case 302:
return;
case 400:
throw new BadRequestException("Bad Request: " + address);
case 403:
throw new ForbiddenException(address + " returned 403");
case 404:
throw new NotFoundException(address + " returned a 404, ensure that your server is connected to an up to date Plan server.");
case 500:
throw new IllegalStateException(); // Not supported
default:
throw new WebException(address + "| Wrong response code " + responseCode);
}
} finally {
connection.disconnect();
}
}
default String login(String address) throws IOException, KeyManagementException, NoSuchAlgorithmException {
HttpURLConnection loginConnection = null;
String cookie = "";
try {
loginConnection = connector.getConnection("GET", address + "/auth/login?user=test&password=testPass");
try (InputStream in = loginConnection.getInputStream()) {
String responseBody = new String(IOUtils.toByteArray(in));
assertTrue(responseBody.contains("\"success\":true"), () -> "Not successful: " + responseBody);
cookie = loginConnection.getHeaderField("Set-Cookie").split(";")[0];
System.out.println("Got cookie: " + cookie);
}
} finally {
loginConnection.disconnect();
}
return cookie;
}
}

View File

@ -17,7 +17,7 @@
package com.djrapitops.plan.delivery.webserver;
import com.djrapitops.plan.PlanSystem;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.settings.config.PlanConfig;
import com.djrapitops.plan.settings.config.paths.WebserverSettings;
import com.djrapitops.plan.storage.database.transactions.commands.RegisterWebUserTransaction;
@ -31,6 +31,7 @@ import utilities.mocks.PluginMockComponent;
import java.io.File;
import java.nio.file.Path;
import java.util.Collections;
class JksHttpsServerTest implements HttpsServerTest {
@ -58,8 +59,8 @@ class JksHttpsServerTest implements HttpsServerTest {
system.enable();
WebUser webUser = new WebUser("test", PassEncryptUtil.createHash("testPass"), 0);
system.getDatabaseSystem().getDatabase().executeTransaction(new RegisterWebUserTransaction(webUser, ));
User user = new User("test", "console", null, PassEncryptUtil.createHash("testPass"), 0, Collections.emptyList());
system.getDatabaseSystem().getDatabase().executeTransaction(new RegisterWebUserTransaction(user));
}
@AfterAll

View File

@ -17,7 +17,7 @@
package com.djrapitops.plan.delivery.webserver;
import com.djrapitops.plan.PlanSystem;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.settings.config.PlanConfig;
import com.djrapitops.plan.settings.config.changes.ConfigUpdater;
import com.djrapitops.plan.settings.config.paths.WebserverSettings;
@ -34,6 +34,7 @@ import java.io.File;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardCopyOption;
import java.util.Collections;
class Pkcs12HttpsServerTest implements HttpsServerTest {
@ -63,8 +64,8 @@ class Pkcs12HttpsServerTest implements HttpsServerTest {
system.enable();
WebUser webUser = new WebUser("test", PassEncryptUtil.createHash("testPass"), 0);
system.getDatabaseSystem().getDatabase().executeTransaction(new RegisterWebUserTransaction(webUser, ));
User user = new User("test", "console", null, PassEncryptUtil.createHash("testPass"), 0, Collections.emptyList());
system.getDatabaseSystem().getDatabase().executeTransaction(new RegisterWebUserTransaction(user));
}
@AfterAll

View File

@ -17,7 +17,7 @@
package com.djrapitops.plan.storage.database.queries;
import com.djrapitops.plan.delivery.domain.DateObj;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.gathering.domain.GeoInfo;
import com.djrapitops.plan.gathering.domain.Session;
import com.djrapitops.plan.gathering.domain.TPS;
@ -29,6 +29,7 @@ import com.djrapitops.plan.storage.database.queries.objects.*;
import com.djrapitops.plan.storage.database.transactions.BackupCopyTransaction;
import com.djrapitops.plan.storage.database.transactions.commands.RegisterWebUserTransaction;
import com.djrapitops.plan.storage.database.transactions.events.*;
import com.djrapitops.plan.utilities.PassEncryptUtil;
import com.google.common.util.concurrent.MoreExecutors;
import org.junit.jupiter.api.Test;
import utilities.RandomData;
@ -67,8 +68,8 @@ public interface DatabaseBackupTest extends DatabaseTestPreparer {
Collections.singletonList(new DateObj<>(System.currentTimeMillis(), RandomData.randomInt(-1, 40))))
);
WebUser webUser = new WebUser(TestConstants.PLAYER_ONE_NAME, RandomData.randomString(100), 0);
db().executeTransaction(new RegisterWebUserTransaction(webUser, ));
User user = new User("test", "console", null, PassEncryptUtil.createHash("testPass"), 0, Collections.emptyList());
db().executeTransaction(new RegisterWebUserTransaction(user));
}
@Test
@ -92,7 +93,7 @@ public interface DatabaseBackupTest extends DatabaseTestPreparer {
assertQueryResultIsEqual(db(), backup, LargeFetchQueries.fetchAllWorldNames());
assertQueryResultIsEqual(db(), backup, LargeFetchQueries.fetchAllTPSData());
assertQueryResultIsEqual(db(), backup, ServerQueries.fetchPlanServerInformation());
assertQueryResultIsEqual(db(), backup, WebUserQueries.fetchAllPlanWebUsers());
assertQueryResultIsEqual(db(), backup, WebUserQueries.fetchAllUsers());
} finally {
backup.close();
}
@ -119,7 +120,7 @@ public interface DatabaseBackupTest extends DatabaseTestPreparer {
assertQueryResultIsEqual(db(), backup, LargeFetchQueries.fetchAllWorldNames());
assertQueryResultIsEqual(db(), backup, LargeFetchQueries.fetchAllTPSData());
assertQueryResultIsEqual(db(), backup, ServerQueries.fetchPlanServerInformation());
assertQueryResultIsEqual(db(), backup, WebUserQueries.fetchAllPlanWebUsers());
assertQueryResultIsEqual(db(), backup, WebUserQueries.fetchAllUsers());
} finally {
backup.close();
}

View File

@ -17,11 +17,13 @@
package com.djrapitops.plan.storage.database.queries;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.auth.User;
import com.djrapitops.plan.storage.database.DatabaseTestPreparer;
import com.djrapitops.plan.storage.database.queries.objects.WebUserQueries;
import com.djrapitops.plan.storage.database.transactions.commands.RegisterWebUserTransaction;
import com.djrapitops.plan.storage.database.transactions.commands.RemoveEverythingTransaction;
import com.djrapitops.plan.storage.database.transactions.commands.RemoveWebUserTransaction;
import com.djrapitops.plan.utilities.PassEncryptUtil;
import org.junit.jupiter.api.Test;
import utilities.TestConstants;
@ -32,33 +34,34 @@ import static org.junit.jupiter.api.Assertions.*;
public interface WebUserQueriesTest extends DatabaseTestPreparer {
@Test
default void webUserIsRegistered() {
WebUser expected = new WebUser(TestConstants.PLAYER_ONE_NAME, "RandomGarbageBlah", 0);
db().executeTransaction(new RegisterWebUserTransaction(expected, ));
default void userIsRegistered() {
String username = TestConstants.PLAYER_ONE_NAME;
User expected = new User(username, "console", null, PassEncryptUtil.createHash("testPass"), 0, WebUser.getPermissionsForLevel(0));
db().executeTransaction(new RegisterWebUserTransaction(expected));
forcePersistenceCheck();
Optional<WebUser> found = db().query(WebUserQueries.fetchWebUser(TestConstants.PLAYER_ONE_NAME));
Optional<User> found = db().query(WebUserQueries.fetchUser(username));
assertTrue(found.isPresent());
assertEquals(expected, found.get());
}
@Test
default void multipleWebUsersAreFetchedAppropriately() {
webUserIsRegistered();
assertEquals(1, db().query(WebUserQueries.fetchAllPlanWebUsers()).size());
userIsRegistered();
assertEquals(1, db().query(WebUserQueries.fetchAllUsers()).size());
}
@Test
default void webUserIsRemoved() {
webUserIsRegistered();
userIsRegistered();
db().executeTransaction(new RemoveWebUserTransaction(TestConstants.PLAYER_ONE_NAME));
assertFalse(db().query(WebUserQueries.fetchWebUser(TestConstants.PLAYER_ONE_NAME)).isPresent());
assertFalse(db().query(WebUserQueries.fetchUser(TestConstants.PLAYER_ONE_NAME)).isPresent());
}
@Test
default void removeEverythingRemovesWebUser() {
webUserIsRegistered();
userIsRegistered();
db().executeTransaction(new RemoveEverythingTransaction());
assertTrue(db().query(WebUserQueries.fetchAllPlanWebUsers()).isEmpty());
assertTrue(db().query(WebUserQueries.fetchAllUsers()).isEmpty());
}
}

View File

@ -16,7 +16,6 @@
*/
package com.djrapitops.plan.utilities.comparators;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.domain.keys.SessionKeys;
import com.djrapitops.plan.delivery.rendering.json.graphs.line.Point;
import com.djrapitops.plan.gathering.domain.GeoInfo;
@ -25,7 +24,6 @@ import com.djrapitops.plan.gathering.domain.TPS;
import com.djrapitops.plan.settings.locale.Message;
import com.djrapitops.plan.settings.locale.lang.CmdHelpLang;
import com.djrapitops.plan.settings.locale.lang.Lang;
import com.djrapitops.plan.utilities.PassEncryptUtil;
import com.djrapitops.plan.utilities.java.Lists;
import org.junit.jupiter.api.Test;
import utilities.RandomData;
@ -78,20 +76,6 @@ class ComparatorTest {
assertEquals(expected, result);
}
@Test
void webUserComparator() throws PassEncryptUtil.CannotPerformOperationException {
List<WebUser> webUsers = RandomData.randomWebUsers();
List<Integer> expected = webUsers.stream().map(WebUser::getPermLevel)
.sorted(Integer::compare).collect(Collectors.toList());
Collections.reverse(expected);
webUsers.sort(new WebUserComparator());
List<Integer> result = Lists.map(webUsers, WebUser::getPermLevel);
assertEquals(expected, result);
}
@Test
void stringLengthComparator() {
List<Integer> result = Stream.of(

View File

@ -18,11 +18,9 @@ package utilities;
import com.djrapitops.plan.delivery.domain.DateObj;
import com.djrapitops.plan.delivery.domain.Nickname;
import com.djrapitops.plan.delivery.domain.WebUser;
import com.djrapitops.plan.delivery.rendering.json.graphs.line.Point;
import com.djrapitops.plan.gathering.domain.*;
import com.djrapitops.plan.storage.database.sql.tables.KillsTable;
import com.djrapitops.plan.utilities.PassEncryptUtil;
import org.apache.commons.lang3.RandomStringUtils;
import java.util.*;
@ -66,14 +64,6 @@ public class RandomData {
return new Nickname(randomString(randomInt(50, 100)), randomTime(), serverUUID);
}
public static List<WebUser> randomWebUsers() throws PassEncryptUtil.CannotPerformOperationException {
List<WebUser> test = new ArrayList<>();
for (int i = 0; i < 20; i++) {
test.add(new WebUser(randomString(5), PassEncryptUtil.createHash(randomString(7)), r.nextInt()));
}
return test;
}
public static List<TPS> randomTPS() {
List<TPS> test = new ArrayList<>();
for (int i = 0; i < randomInt(5, 100); i++) {