Add simple version comparison algorithm

This commit is contained in:
Kai S. K. Engelbart 2020-06-20 14:38:06 +02:00
parent e1775245b0
commit d8d0d2f66a

View File

@ -8,6 +8,7 @@ import java.time.LocalDateTime;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashSet; import java.util.HashSet;
import java.util.logging.Logger; import java.util.logging.Logger;
import java.util.regex.Pattern;
import javax.persistence.NoResultException; import javax.persistence.NoResultException;
@ -38,9 +39,8 @@ public final class LoginCredentialProcessor implements ObjectProcessor<LoginCred
private final PersistenceManager persistenceManager = PersistenceManager.getInstance(); private final PersistenceManager persistenceManager = PersistenceManager.getInstance();
private final ConnectionManager connectionManager = ConnectionManager.getInstance(); private final ConnectionManager connectionManager = ConnectionManager.getInstance();
private static final Logger logger = EnvoyLog.getLogger(LoginCredentialProcessor.class); private static final Logger logger = EnvoyLog.getLogger(LoginCredentialProcessor.class);
// private static final Pattern versionPattern = private static final Pattern versionPattern = Pattern.compile("(?<major>\\d).(?<minor>\\d)(?:-(?<suffix>\\w+))?");
// Pattern.compile("v(?<major>\\d).(?<minor>\\d)(?:-(?<suffix>\\w+))?");
@Override @Override
public void process(LoginCredentials credentials, long socketID, ObjectWriteProxy writeProxy) throws IOException { public void process(LoginCredentials credentials, long socketID, ObjectWriteProxy writeProxy) throws IOException {
@ -49,10 +49,10 @@ public final class LoginCredentialProcessor implements ObjectProcessor<LoginCred
UserStatusChangeProcessor.setWriteProxy(writeProxy); UserStatusChangeProcessor.setWriteProxy(writeProxy);
// TODO: Verify compatibility // TODO: Verify compatibility
if (Startup.MIN_CLIENT_VERSION.compareTo(credentials.getClientVersion()) <= 0 if (!verifyCompatibility(credentials.getClientVersion())) {
&& Startup.MAX_CLIENT_VERSION.compareTo(credentials.getClientVersion()) >= 0) { logger.info("The client has the wrong version.");
// writeProxy.write(socketID, new HandshakeRejectionEvent("Wrong version")); writeProxy.write(socketID, new HandshakeRejection("Wrong version"));
// return; return;
} }
// Acquire a user object (or reject the handshake if that's impossible) // Acquire a user object (or reject the handshake if that's impossible)
@ -125,6 +125,57 @@ public final class LoginCredentialProcessor implements ObjectProcessor<LoginCred
} }
} }
private boolean verifyCompatibility(String version) {
final var currentMatcher = versionPattern.matcher(version);
if (!currentMatcher.matches()) return false;
final var minMatcher = versionPattern.matcher(Startup.MIN_CLIENT_VERSION);
final var maxMatcher = versionPattern.matcher(Startup.MAX_CLIENT_VERSION);
if (!minMatcher.matches() || !maxMatcher.matches()) throw new RuntimeException("Invalid min or max client version configured!");
// Compare suffixes
{
final var currentSuffix = convertSuffix(currentMatcher.group("suffix"));
final var minSuffix = convertSuffix(minMatcher.group("suffix"));
final var maxSuffix = convertSuffix(maxMatcher.group("suffix"));
if (currentSuffix < minSuffix || currentSuffix > maxSuffix) return false;
}
// Compare major
{
final var currentMajor = Integer.parseInt(currentMatcher.group("major"));
final var minMajor = Integer.parseInt(minMatcher.group("major"));
final var maxMajor = Integer.parseInt(maxMatcher.group("major"));
if (currentMajor < minMajor || currentMajor > maxMajor) return false;
}
// Compare minor
{
final var currentMinor = Integer.parseInt(currentMatcher.group("minor"));
final var minMinor = Integer.parseInt(minMatcher.group("minor"));
final var maxMinor = Integer.parseInt(maxMatcher.group("minor"));
if (currentMinor < minMinor || currentMinor > maxMinor) return false;
}
return true;
}
private int convertSuffix(String suffix) {
switch (suffix == null ? "" : suffix) {
case "alpha":
return 0;
case "beta":
return 1;
default:
return 2;
}
}
@Override @Override
public Class<LoginCredentials> getInputClass() { return LoginCredentials.class; } public Class<LoginCredentials> getInputClass() { return LoginCredentials.class; }
} }