Use Instant instead of long for time measurement
This commit is contained in:
@@ -22,70 +22,60 @@ package net.server.coordinator.login;
|
||||
import config.YamlConfig;
|
||||
import net.server.Server;
|
||||
|
||||
import java.time.Instant;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Ronan
|
||||
*/
|
||||
public class LoginStorage {
|
||||
|
||||
private ConcurrentHashMap<Integer, List<Long>> loginHistory = new ConcurrentHashMap<>();
|
||||
private final ConcurrentHashMap<Integer, List<Instant>> loginHistory = new ConcurrentHashMap<>(); // Key: accountId
|
||||
|
||||
public boolean registerLogin(int accountId) {
|
||||
List<Long> accHist = loginHistory.get(accountId);
|
||||
if (accHist == null) {
|
||||
accHist = new LinkedList<>();
|
||||
loginHistory.put(accountId, accHist);
|
||||
}
|
||||
|
||||
synchronized (accHist) {
|
||||
if (accHist.size() > YamlConfig.config.server.MAX_ACCOUNT_LOGIN_ATTEMPT) {
|
||||
long blockExpiration = Server.getInstance().getCurrentTime() + YamlConfig.config.server.LOGIN_ATTEMPT_DURATION;
|
||||
Collections.fill(accHist, blockExpiration);
|
||||
List<Instant> attempts = loginHistory.computeIfAbsent(accountId, k -> new ArrayList<>());
|
||||
|
||||
synchronized (attempts) {
|
||||
final Instant attemptExpiry = Instant.ofEpochMilli(Server.getInstance().getCurrentTime() + YamlConfig.config.server.LOGIN_ATTEMPT_DURATION);
|
||||
|
||||
if (attempts.size() > YamlConfig.config.server.MAX_ACCOUNT_LOGIN_ATTEMPT) {
|
||||
Collections.fill(attempts, attemptExpiry);
|
||||
return false;
|
||||
}
|
||||
|
||||
accHist.add(Server.getInstance().getCurrentTime() + YamlConfig.config.server.LOGIN_ATTEMPT_DURATION);
|
||||
attempts.add(attemptExpiry);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
public void updateLoginHistory() {
|
||||
long timeNow = Server.getInstance().getCurrentTime();
|
||||
List<Integer> toRemove = new LinkedList<>();
|
||||
List<Long> toRemoveAttempt = new LinkedList<>();
|
||||
|
||||
for (Entry<Integer, List<Long>> loginEntries : loginHistory.entrySet()) {
|
||||
toRemoveAttempt.clear();
|
||||
|
||||
List<Long> accAttempts = loginEntries.getValue();
|
||||
synchronized (accAttempts) {
|
||||
for (Long loginAttempt : accAttempts) {
|
||||
if (loginAttempt < timeNow) {
|
||||
toRemoveAttempt.add(loginAttempt);
|
||||
}
|
||||
public void clearExpiredAttempts() {
|
||||
final Instant now = Instant.ofEpochMilli(Server.getInstance().getCurrentTime());
|
||||
List<Integer> accountIdsToClear = new ArrayList<>();
|
||||
|
||||
for (Entry<Integer, List<Instant>> loginEntries : loginHistory.entrySet()) {
|
||||
final List<Instant> attempts = loginEntries.getValue();
|
||||
synchronized (attempts) {
|
||||
List<Instant> attemptsToRemove = attempts.stream()
|
||||
.filter(attempt -> attempt.isBefore(now))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
for (Instant attemptToRemove : attemptsToRemove) {
|
||||
attempts.remove(attemptToRemove);
|
||||
}
|
||||
|
||||
if (!toRemoveAttempt.isEmpty()) {
|
||||
for (Long trAttempt : toRemoveAttempt) {
|
||||
accAttempts.remove(trAttempt);
|
||||
}
|
||||
|
||||
if (accAttempts.isEmpty()) {
|
||||
toRemove.add(loginEntries.getKey());
|
||||
}
|
||||
if (attempts.isEmpty()) {
|
||||
accountIdsToClear.add(loginEntries.getKey());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (Integer tr : toRemove) {
|
||||
loginHistory.remove(tr);
|
||||
|
||||
for (Integer accountId : accountIdsToClear) {
|
||||
loginHistory.remove(accountId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -399,7 +399,7 @@ public class MapleSessionCoordinator {
|
||||
}
|
||||
|
||||
public void runUpdateLoginHistory() {
|
||||
loginStorage.updateLoginHistory();
|
||||
loginStorage.clearExpiredAttempts();
|
||||
}
|
||||
|
||||
public void printSessionTrace() {
|
||||
|
||||
Reference in New Issue
Block a user