Better login management

This commit is contained in:
Andrea Cavalli 2020-10-17 01:53:14 +02:00
parent d9e0faafb7
commit a7223c4d83
4 changed files with 86 additions and 43 deletions

View File

@ -34,6 +34,7 @@ import it.tdlight.tdlibsession.FatalErrorType;
import it.tdlight.tdlibsession.td.TdResult;
import it.tdlight.tdlibsession.td.middle.AsyncTdMiddle;
import it.tdlight.utils.MonoUtils;
import it.tdlight.utils.TdLightUtils;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
@ -348,7 +349,6 @@ public class AsyncTdEasy {
.filter(obj -> obj.getConstructor() == UpdateAuthorizationState.CONSTRUCTOR)
.map(obj -> ((UpdateAuthorizationState) obj).authorizationState)
.flatMap(obj -> {
this.authState.onNext(new AuthorizationStateReady());
switch (obj.getConstructor()) {
case AuthorizationStateWaitTdlibParameters.CONSTRUCTOR:
return MonoUtils.thenOrError(Mono.from(this.settings).map(settings -> {
@ -371,7 +371,12 @@ public class AsyncTdEasy {
return new SetTdlibParameters(parameters);
}).flatMap(this::sendDirectly));
case AuthorizationStateWaitEncryptionKey.CONSTRUCTOR:
return MonoUtils.thenOrError(sendDirectly(new CheckDatabaseEncryptionKey()));
return MonoUtils
.thenOrError(sendDirectly(new CheckDatabaseEncryptionKey()))
.onErrorResume((error) -> {
logger.error("Error while checking TDLib encryption key", error);
return sendDirectly(new TdApi.Close()).then();
});
case AuthorizationStateWaitPhoneNumber.CONSTRUCTOR:
return MonoUtils.thenOrError(Mono.from(this.settings).flatMap(settings -> {
if (settings.isPhoneNumberSet()) {
@ -383,7 +388,10 @@ public class AsyncTdEasy {
} else {
return Mono.error(new IllegalArgumentException("A bot is neither an user or a bot"));
}
}));
})).onErrorResume((error) -> {
logger.error("Error while waiting for phone number", error);
return sendDirectly(new TdApi.Close()).then();
});
case AuthorizationStateWaitRegistration.CONSTRUCTOR:
var authorizationStateWaitRegistration = (AuthorizationStateWaitRegistration) obj;
RegisterUser registerUser = new RegisterUser();
@ -396,7 +404,7 @@ public class AsyncTdEasy {
.from(settings)
.map(TdEasySettings::getParameterRequestHandler)
.flatMap(handler -> {
return handler
return MonoUtils.thenOrLogRepeatError(() -> handler
.onParameterRequest(Parameter.ASK_FIRST_NAME, new ParameterInfoEmpty())
.filter(Objects::nonNull)
.map(String::trim)
@ -414,9 +422,8 @@ public class AsyncTdEasy {
.defaultIfEmpty("")
.doOnNext(lastName -> registerUser.lastName = lastName)
)
.thenReturn(handler);
})
.then(MonoUtils.thenOrError(sendDirectly(registerUser)));
.then(sendDirectly(registerUser)));
});
case TdApi.AuthorizationStateWaitOtherDeviceConfirmation.CONSTRUCTOR:
var authorizationStateWaitOtherDeviceConfirmation = (AuthorizationStateWaitOtherDeviceConfirmation) obj;
return Mono
@ -433,27 +440,26 @@ public class AsyncTdEasy {
.from(settings)
.map(TdEasySettings::getParameterRequestHandler)
.flatMap(handler -> {
return handler.onParameterRequest(Parameter.ASK_CODE,
return MonoUtils.thenOrLogRepeatError(() -> handler.onParameterRequest(Parameter.ASK_CODE,
new ParameterInfoCode(authorizationStateWaitCode.codeInfo.phoneNumber,
authorizationStateWaitCode.codeInfo.nextType,
authorizationStateWaitCode.codeInfo.timeout,
authorizationStateWaitCode.codeInfo.type
)
);
})
.flatMap(code -> MonoUtils.thenOrError(sendDirectly(new CheckAuthenticationCode(code))));
).flatMap(code -> sendDirectly(new CheckAuthenticationCode(code))));
});
case AuthorizationStateWaitPassword.CONSTRUCTOR:
var authorizationStateWaitPassword = (AuthorizationStateWaitPassword) obj;
return Mono
.from(settings)
.map(TdEasySettings::getParameterRequestHandler)
.flatMap(handler -> {
return handler.onParameterRequest(Parameter.ASK_PASSWORD,
return MonoUtils.thenOrLogRepeatError(() -> handler.onParameterRequest(Parameter.ASK_PASSWORD,
new ParameterInfoPasswordHint(authorizationStateWaitPassword.passwordHint)
);
})
.flatMap(password -> MonoUtils.thenOrError(sendDirectly(new CheckAuthenticationPassword(password))));
).flatMap(password -> sendDirectly(new CheckAuthenticationPassword(password))));
});
case AuthorizationStateReady.CONSTRUCTOR: {
this.authState.onNext(new AuthorizationStateReady());
return Mono.empty();
}
case AuthorizationStateClosed.CONSTRUCTOR:

View File

@ -8,12 +8,15 @@ import it.tdlight.jni.TdApi;
import it.tdlight.jni.TdApi.Object;
import it.tdlight.tdlibsession.td.TdError;
import it.tdlight.tdlibsession.td.TdResult;
import it.tdlight.tdlibsession.td.middle.direct.AsyncTdMiddleDirect;
import java.util.Objects;
import java.util.concurrent.CompletableFuture;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.Supplier;
import org.reactivestreams.Subscription;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.warp.commonutils.concurrency.future.CompletableFutureUtils;
import reactor.core.CoreSubscriber;
import reactor.core.publisher.Mono;
@ -23,6 +26,8 @@ import reactor.util.context.Context;
public class MonoUtils {
private static final Logger logger = LoggerFactory.getLogger(MonoUtils.class);
public static <T> Handler<AsyncResult<T>> toHandler(SynchronousSink<T> sink) {
return event -> {
if (event.succeeded()) {
@ -137,6 +142,26 @@ public class MonoUtils {
});
}
public static <T extends TdApi.Object> Mono<Void> thenOrLogSkipError(Mono<TdResult<T>> optionalMono) {
return optionalMono.handle((optional, sink) -> {
if (optional.failed()) {
logger.error("Received TDLib error: {}", optional.cause());
}
sink.complete();
});
}
public static <T extends TdApi.Object> Mono<Void> thenOrLogRepeatError(Supplier<? extends Mono<TdResult<T>>> optionalMono) {
return Mono.defer(() -> optionalMono.get().handle((TdResult<T> optional, SynchronousSink<Void> sink) -> {
if (optional.succeeded()) {
sink.complete();
} else {
logger.error("Received TDLib error: {}", optional.cause());
sink.error(new TdError(optional.cause().code, optional.cause().message));
}
})).retry();
}
public static <T> Mono<T> fromFuture(CompletableFuture<T> future) {
return Mono.create(sink -> {
future.whenComplete((result, error) -> {

View File

@ -0,0 +1,40 @@
package it.tdlight.utils;
import it.tdlight.jni.TdApi;
import it.tdlight.jni.TdApi.Error;
import it.tdlight.tdlibsession.td.ResponseError;
import it.tdlight.tdlibsession.td.TdError;
import org.jetbrains.annotations.Nullable;
public class TdLightUtils {
@SuppressWarnings("RedundantIfStatement")
public static boolean errorEquals(Throwable ex, @Nullable Integer errorCode, @Nullable String errorText) {
while (ex != null) {
TdApi.Error error = null;
if (ex instanceof TdError) {
error = ((TdError) ex).getTdError();
}
if (ex instanceof ResponseError) {
error = new Error(((ResponseError) ex).getErrorCode(), ((ResponseError) ex).getErrorMessage());
}
if (error != null) {
if (errorCode != null) {
if (error.code != errorCode) {
return false;
}
}
if (errorText != null) {
if (error.message == null || !error.message.contains(errorText)) {
return false;
}
}
return true;
}
ex = ex.getCause();
}
return false;
}
}

View File

@ -1,28 +0,0 @@
module it.tdlight.tdlibsessioncontainer {
requires vertx.core;
requires org.jetbrains.annotations;
requires reactor.core;
requires tdlight.java;
requires org.slf4j;
requires org.reactivestreams;
requires org.apache.logging.log4j.core;
requires org.apache.logging.log4j;
requires common.utils;
requires vertx.circuit.breaker;
requires org.apache.commons.lang3;
requires com.hazelcast.core;
requires vertx.hazelcast;
requires it.unimi.dsi.fastutil;
requires com.google.gson;
exports it.tdlight.tdlibsession;
exports it.tdlight.tdlibsession.remoteclient;
exports it.tdlight.tdlibsession.td;
exports it.tdlight.tdlibsession.td.direct;
exports it.tdlight.tdlibsession.td.easy;
exports it.tdlight.tdlibsession.td.middle;
exports it.tdlight.tdlibsession.td.middle.client;
exports it.tdlight.tdlibsession.td.middle.direct;
exports it.tdlight.tdlibsession.td.middle.server;
exports it.tdlight.utils;
}