Unify ban handling on login

This commit is contained in:
P0nk
2024-09-29 17:54:20 +02:00
parent 50524a7740
commit a307afae3c
7 changed files with 35 additions and 97 deletions

View File

@@ -61,7 +61,6 @@ import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.time.LocalDate;
import java.util.Arrays;
import java.util.Calendar;
@@ -504,37 +503,6 @@ public class Client extends ChannelInboundHandlerAdapter {
return ++failedLoginAttempts < MAX_FAILED_LOGIN_ATTEMPTS;
}
// TODO: check tempban directly on loaded account
@Deprecated
public Calendar getTempBanCalendarFromDB() {
final Calendar lTempban = Calendar.getInstance();
try (Connection con = DatabaseConnection.getConnection();
PreparedStatement ps = con.prepareStatement("SELECT `tempban` FROM accounts WHERE id = ?")) {
ps.setInt(1, getAccID());
final Timestamp tempban;
try (ResultSet rs = ps.executeQuery()) {
if (!rs.next()) {
return null;
}
tempban = rs.getTimestamp("tempban");
if (tempban.toLocalDateTime().equals(DefaultDates.getTempban())) {
return null;
}
}
lTempban.setTimeInMillis(tempban.getTime());
tempBanCalendar = lTempban;
return lTempban;
} catch (SQLException e) {
e.printStackTrace();
}
return null;//why oh why!?!
}
public Calendar getTempBanCalendar() {
return tempBanCalendar;
}
@@ -800,22 +768,6 @@ public class Client extends ChannelInboundHandlerAdapter {
return false;
}
public final byte getGReason() {
try (Connection con = DatabaseConnection.getConnection();
PreparedStatement ps = con.prepareStatement("SELECT `greason` FROM `accounts` WHERE id = ?")) {
ps.setInt(1, accId);
try (ResultSet rs = ps.executeQuery()) {
if (rs.next()) {
return rs.getByte("greason");
}
}
} catch (SQLException e) {
e.printStackTrace();
}
return 0;
}
public byte getGender() {
return gender;
}

View File

@@ -3,6 +3,7 @@ package database.account;
import client.LoginState;
import lombok.Builder;
import java.time.Instant;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.Objects;
@@ -13,7 +14,7 @@ import java.util.Objects;
@Builder
public record Account(int id, String name, String password, boolean acceptedTos, Byte gender, LocalDate birthdate,
String pin, String pic, byte chrSlots, LoginState loginState, LocalDateTime lastLogin,
boolean banned, Byte banReason, String banDescription, LocalDateTime tempBannedUntil) {
boolean banned, Instant bannedUntil, Byte banReason, String banDescription) {
public Account {
Objects.requireNonNull(name);
Objects.requireNonNull(password);

View File

@@ -20,7 +20,7 @@ public class AccountRepository {
public Optional<Account> findByNameIgnoreCase(String name) {
String sql = """
SELECT id, name, password, pin, pic, birthdate, gender, tos_accepted, chr_slots, login_state,
last_login, banned, ban_reason, ban_description, temp_banned_until
last_login, banned, banned_until, ban_reason, ban_description
FROM account
WHERE lower(name) = lower(:name)""";
try (Handle handle = connection.getHandle()) {
@@ -34,7 +34,7 @@ public class AccountRepository {
public Optional<Account> findById(int accountId) {
String sql = """
SELECT id, name, password, pin, pic, birthdate, gender, tos_accepted, chr_slots, login_state,
last_login, banned, ban_reason, ban_description, temp_banned_until
last_login, banned, banned_until, ban_reason, ban_description
FROM account
WHERE id = :id""";
try (Handle handle = connection.getHandle()) {

View File

@@ -35,11 +35,11 @@ public class AccountRowMapper implements RowMapper<Account> {
.map(Timestamp::toLocalDateTime)
.orElse(null))
.banned(rs.getBoolean("banned"))
.bannedUntil(Optional.ofNullable(rs.getTimestamp("banned_until"))
.map(Timestamp::toInstant)
.orElse(null))
.banReason(rs.getByte("ban_reason"))
.banDescription(rs.getString("ban_description"))
.tempBannedUntil(Optional.ofNullable(rs.getTimestamp("temp_banned_until"))
.map(Timestamp::toLocalDateTime)
.orElse(null))
.build();
}

View File

@@ -48,7 +48,6 @@ import java.sql.Date;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.Calendar;
import java.util.Objects;
import java.util.Optional;
@@ -109,17 +108,12 @@ public final class LoginPasswordHandler implements PacketHandler {
if (account.banned()) {
byte banReason = Objects.requireNonNullElse(account.banReason(), (byte) 0);
c.sendPacket(PacketCreator.getPermBan(banReason));
return;
}
boolean tempBanDisabled = false;
Calendar tempban = null;
if (!tempBanDisabled && (tempban = c.getTempBanCalendarFromDB()) != null) {
if (tempban.getTimeInMillis() > Calendar.getInstance().getTimeInMillis()) {
c.sendPacket(PacketCreator.getTempBan(tempban.getTimeInMillis(), c.getGReason()));
return;
if (account.bannedUntil() != null) {
c.sendPacket(PacketCreator.getTempBan(banReason, account.bannedUntil().toEpochMilli()));
} else {
c.sendPacket(PacketCreator.getPermBan(banReason));
}
return;
}
boolean banCheckDisabled = false;
@@ -128,14 +122,6 @@ public final class LoginPasswordHandler implements PacketHandler {
return;
}
/* TODO: check temp ban from account, something like this:
LocalDateTime tempBan = account.tempBanTimestamp();
if (tempBan != null && tempBan.isAfter(LocalDateTime.now())) {
Duration remainingTempBan = Duration.between(LocalDateTime.now(), tempBan);
c.sendPacket(PacketCreator.getTempBan());
}
*/
if (account.loginState() != LoginState.LOGGED_OUT) {
c.sendPacket(PacketCreator.getLoginFailed(7));
return;

View File

@@ -711,7 +711,7 @@ public class PacketCreator {
return p;
}
public static Packet getTempBan(long timestampTill, byte reason) {
public static Packet getTempBan(byte reason, long timestampTill) {
OutPacket p = OutPacket.create(SendOpcode.LOGIN_STATUS);
p.writeByte(2);
p.writeByte(0);

View File

@@ -1,28 +1,27 @@
CREATE TABLE account
(
id serial NOT NULL,
name varchar(30) NOT NULL,
password varchar(200) NOT NULL,
pin varchar(4),
pic varchar(26),
created_at timestamp DEFAULT now() NOT NULL,
birthdate date NOT NULL,
tos_accepted boolean DEFAULT false NOT NULL,
gender smallint,
chr_slots smallint NOT NULL,
nx_credit integer DEFAULT 0 NOT NULL,
maple_point integer DEFAULT 0 NOT NULL,
nx_prepaid integer DEFAULT 0 NOT NULL,
login_state smallint NOT NULL,
last_login timestamp,
banned boolean DEFAULT false NOT NULL,
ban_reason smallint,
ban_description text,
temp_banned_until timestamp,
greason smallint,
ip text,
hwid text,
macs text,
id serial NOT NULL,
name varchar(30) NOT NULL,
password varchar(200) NOT NULL,
pin varchar(4),
pic varchar(26),
created_at timestamp DEFAULT now() NOT NULL,
birthdate date NOT NULL,
tos_accepted boolean DEFAULT false NOT NULL,
gender smallint,
chr_slots smallint NOT NULL,
nx_credit integer DEFAULT 0 NOT NULL,
maple_point integer DEFAULT 0 NOT NULL,
nx_prepaid integer DEFAULT 0 NOT NULL,
login_state smallint NOT NULL,
last_login timestamp,
banned boolean DEFAULT false NOT NULL,
banned_until timestamp,
ban_reason smallint,
ban_description text,
ip text,
hwid text,
macs text,
PRIMARY KEY (id),
UNIQUE (name)
);