fix: ws timeout #93
@ -16,6 +16,7 @@ import io.smallrye.mutiny.Uni;
|
||||
import io.smallrye.mutiny.unchecked.Unchecked;
|
||||
import jakarta.annotation.PostConstruct;
|
||||
import jakarta.inject.Inject;
|
||||
import jakarta.inject.Named;
|
||||
import jakarta.ws.rs.ForbiddenException;
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
@ -23,6 +24,7 @@ import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.time.Duration;
|
||||
import java.util.*;
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
import static fr.titionfire.ffsaf.net2.Client_Thread.MAPPER;
|
||||
|
||||
@ -51,6 +53,15 @@ public class CompetitionWS {
|
||||
@Inject
|
||||
CompetPermService competPermService;
|
||||
|
||||
@SuppressWarnings("CdiInjectionPointsInspection")
|
||||
@Inject
|
||||
OpenConnections connections;
|
||||
|
||||
@Inject
|
||||
@Named("notify-executor")
|
||||
Executor notifyExecutor;
|
||||
private static Executor executor;
|
||||
|
||||
@Inject
|
||||
CompetitionRepository competitionRepository;
|
||||
|
||||
@ -79,6 +90,8 @@ public class CompetitionWS {
|
||||
getWSReceiverMethods(RCategorie.class, rCategorie);
|
||||
getWSReceiverMethods(RRegister.class, rRegister);
|
||||
getWSReceiverMethods(RCardboard.class, rCardboard);
|
||||
|
||||
executor = notifyExecutor;
|
||||
}
|
||||
|
||||
@OnOpen
|
||||
@ -186,7 +199,7 @@ public class CompetitionWS {
|
||||
// return Uni.createFrom().item(new Message<>(message.uuid(), message.code(), MessageType.REPLY, "ko"));
|
||||
}
|
||||
|
||||
public static Uni<Void> sendNotifyToOtherEditor(WebSocketConnection connection, String code, Object data) {
|
||||
public static void sendNotifyToOtherEditor(WebSocketConnection connection, String code, Object data) {
|
||||
String uuid = connection.pathParam("uuid");
|
||||
|
||||
List<Uni<Void>> queue = new ArrayList<>();
|
||||
@ -198,7 +211,15 @@ public class CompetitionWS {
|
||||
}
|
||||
});
|
||||
|
||||
return Uni.join().all(queue).andCollectFailures().onFailure().recoverWithNull().replaceWithVoid();
|
||||
Uni.join().all(queue)
|
||||
.andCollectFailures()
|
||||
.runSubscriptionOn(executor)
|
||||
.subscribeAsCompletionStage()
|
||||
.whenComplete((v, t) -> {
|
||||
if (t != null) {
|
||||
LOGGER.error("Error sending ws_out message", t);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@OnError
|
||||
|
||||
19
src/main/java/fr/titionfire/ffsaf/ws/ExecutorProducer.java
Normal file
19
src/main/java/fr/titionfire/ffsaf/ws/ExecutorProducer.java
Normal file
@ -0,0 +1,19 @@
|
||||
package fr.titionfire.ffsaf.ws;
|
||||
|
||||
import jakarta.enterprise.inject.Produces;
|
||||
import jakarta.inject.Named;
|
||||
import jakarta.inject.Singleton;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.Executors;
|
||||
|
||||
@Singleton
|
||||
public class ExecutorProducer {
|
||||
|
||||
@Produces
|
||||
@Named("notify-executor")
|
||||
public Executor produceNotifyExecutor() {
|
||||
// Créez un pool de threads avec une taille fixe (par exemple, 10 threads)
|
||||
return Executors.newFixedThreadPool(10);
|
||||
}
|
||||
}
|
||||
@ -80,35 +80,32 @@ public class RCardboard {
|
||||
return Uni.createFrom().nullItem();
|
||||
return Panache.withTransaction(() -> cardboardRepository.persist(cardboardModel));
|
||||
}))
|
||||
.call(model -> SSCardboard.sendCardboard(connection, CardboardEntity.fromModel(model)))
|
||||
.invoke(model -> SSCardboard.sendCardboard(connection, CardboardEntity.fromModel(model)))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@WSReceiver(code = "getCardboardWithoutThis", permission = PermLevel.VIEW)
|
||||
public Uni<CardboardAllMatch> getCardboardWithoutThis(WebSocketConnection connection, Long matchId) {
|
||||
return getById(matchId, connection)
|
||||
.chain(matchModel -> cardboardRepository.list("compet = ?1 AND match != ?2", matchModel.getCategory().getCompet(), matchModel)
|
||||
.chain(matchModel -> cardboardRepository.list("compet = ?1 AND match != ?2",
|
||||
matchModel.getCategory().getCompet(), matchModel)
|
||||
.map(models -> {
|
||||
CardboardAllMatch out = new CardboardAllMatch();
|
||||
|
||||
models.stream().filter(c -> (matchModel.getC1_id() != null
|
||||
&& Objects.equals(c.getComb(), matchModel.getC1_id()))
|
||||
|| (matchModel.getC1_guest() != null
|
||||
&& Objects.equals(c.getGuestComb(), matchModel.getC1_guest())))
|
||||
.forEach(c -> {
|
||||
for (CardboardModel c : models) {
|
||||
if ((matchModel.getC1_id() != null && Objects.equals(c.getComb(),
|
||||
matchModel.getC1_id())) || (matchModel.getC1_guest() != null && Objects.equals(
|
||||
c.getGuestComb(), matchModel.getC1_guest()))) {
|
||||
out.c1_yellow += c.getYellow();
|
||||
out.c1_red += c.getRed();
|
||||
});
|
||||
|
||||
models.stream().filter(c -> (matchModel.getC2_id() != null
|
||||
&& Objects.equals(c.getComb(), matchModel.getC2_id()))
|
||||
|| (matchModel.getC2_guest() != null
|
||||
&& Objects.equals(c.getGuestComb(), matchModel.getC2_guest())))
|
||||
.forEach(c -> {
|
||||
}
|
||||
if ((matchModel.getC2_id() != null && Objects.equals(c.getComb(),
|
||||
matchModel.getC2_id())) || (matchModel.getC2_guest() != null && Objects.equals(
|
||||
c.getGuestComb(), matchModel.getC2_guest()))) {
|
||||
out.c2_yellow += c.getYellow();
|
||||
out.c2_red += c.getRed();
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
return out;
|
||||
}));
|
||||
}
|
||||
|
||||
@ -97,7 +97,7 @@ public class RCategorie {
|
||||
|
||||
return categoryRepository.create(categoryModel);
|
||||
})
|
||||
.call(cat -> SSCategorie.sendAddCategory(connection, cat))
|
||||
.invoke(cat -> SSCategorie.sendAddCategory(connection, cat))
|
||||
.map(CategoryModel::getId);
|
||||
}
|
||||
|
||||
@ -121,7 +121,7 @@ public class RCategorie {
|
||||
Uni<Long> finalUni = uni;
|
||||
return Panache.withTransaction(() -> finalUni);
|
||||
})
|
||||
.call(cat -> SSCategorie.sendCategory(connection, cat))
|
||||
.invoke(cat -> SSCategorie.sendCategory(connection, cat))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -202,7 +202,7 @@ public class RCategorie {
|
||||
.call(__ -> treeRepository.flush())
|
||||
.call(cat -> treeRepository.list("category = ?1 AND level != 0", cat.getId())
|
||||
.map(treeModels -> treeModels.stream().map(TreeEntity::fromModel).toList())
|
||||
.chain(trees -> SSCategorie.sendTreeCategory(connection, trees)))
|
||||
.invoke(trees -> SSCategorie.sendTreeCategory(connection, trees)))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -212,7 +212,7 @@ public class RCategorie {
|
||||
.call(cat -> Panache.withTransaction(() -> treeRepository.delete("category = ?1", cat.getId())
|
||||
.call(__ -> matchRepository.delete("category = ?1", cat))))
|
||||
.chain(cat -> Panache.withTransaction(() -> categoryRepository.delete(cat)))
|
||||
.call(__ -> SSCategorie.sendDelCategory(connection, id))
|
||||
.invoke(__ -> SSCategorie.sendDelCategory(connection, id))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
|
||||
@ -84,7 +84,7 @@ public class RMatch {
|
||||
}))
|
||||
.chain(categoryModel -> creatMatch(categoryModel, m))
|
||||
.chain(mm -> Panache.withTransaction(() -> matchRepository.create(mm)))
|
||||
.call(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.invoke(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -121,7 +121,7 @@ public class RMatch {
|
||||
mm.setC2_guest(null);
|
||||
}))
|
||||
.chain(mm -> Panache.withTransaction(() -> matchRepository.persist(mm)))
|
||||
.call(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.invoke(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -136,7 +136,7 @@ public class RMatch {
|
||||
m.getCategory_ord()))
|
||||
.invoke(m -> m.setCategory_ord(order.pos))
|
||||
.call(m -> Panache.withTransaction(() -> matchRepository.persist(m)))
|
||||
.call(mm -> SSMatch.sendMatchOrder(connection, order))
|
||||
.invoke(mm -> SSMatch.sendMatchOrder(connection, order))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -163,12 +163,12 @@ public class RMatch {
|
||||
.call(mm -> {
|
||||
if (mm.isEnd() && mm.win() != old_win && mm.getCategory_ord() == -42) {
|
||||
return updateEndAndTree(mm, new ArrayList<>())
|
||||
.call(l -> SSMatch.sendMatch(connection, l));
|
||||
.invoke(l -> SSMatch.sendMatch(connection, l));
|
||||
}
|
||||
return Uni.createFrom().nullItem();
|
||||
});
|
||||
})
|
||||
.call(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.invoke(mm -> SSMatch.sendMatch(connection, MatchEntity.fromModel(mm)))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -189,7 +189,7 @@ public class RMatch {
|
||||
})
|
||||
.invoke(mm -> toSend.add(MatchEntity.fromModel(mm)))
|
||||
.chain(mm -> updateEndAndTree(mm, toSend))
|
||||
.call(__ -> SSMatch.sendMatch(connection, toSend))
|
||||
.invoke(__ -> SSMatch.sendMatch(connection, toSend))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -278,7 +278,7 @@ public class RMatch {
|
||||
public Uni<Void> deleteMatch(WebSocketConnection connection, Long idMatch) {
|
||||
return getById(idMatch, connection)
|
||||
.chain(matchModel -> Panache.withTransaction(() -> matchRepository.delete(matchModel)))
|
||||
.call(__ -> SSMatch.sendDeleteMatch(connection, idMatch))
|
||||
.invoke(__ -> SSMatch.sendDeleteMatch(connection, idMatch))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
@ -295,7 +295,7 @@ public class RMatch {
|
||||
.call(cm -> data.matchesToRemove.isEmpty() ? Uni.createFrom().voidItem() :
|
||||
(Panache.withTransaction(
|
||||
() -> matchRepository.delete("id IN ?1 AND category = ?2", data.matchesToRemove, cm))
|
||||
.call(__ -> SSMatch.sendDeleteMatch(connection, data.matchesToRemove))))
|
||||
.invoke(__ -> SSMatch.sendDeleteMatch(connection, data.matchesToRemove))))
|
||||
.call(cm -> Panache.withSession(() -> matchRepository.list("id IN ?1 AND category = ?2",
|
||||
Stream.concat(data.matchOrderToUpdate.keySet().stream(),
|
||||
data.matchPouleToUpdate.keySet().stream())
|
||||
@ -321,7 +321,7 @@ public class RMatch {
|
||||
.chain(mm -> mm.isEmpty() ? Uni.createFrom().voidItem() :
|
||||
Panache.withTransaction(() -> matchRepository.create(mm))
|
||||
.invoke(__ -> matches.addAll(mm.stream().map(MatchEntity::fromModel).toList())))
|
||||
.call(__ -> SSMatch.sendMatch(connection, matches))
|
||||
.invoke(__ -> SSMatch.sendMatch(connection, matches))
|
||||
.replaceWithVoid();
|
||||
}
|
||||
|
||||
|
||||
@ -3,11 +3,10 @@ package fr.titionfire.ffsaf.ws.send;
|
||||
import fr.titionfire.ffsaf.domain.entity.CardboardEntity;
|
||||
import fr.titionfire.ffsaf.ws.CompetitionWS;
|
||||
import io.quarkus.websockets.next.WebSocketConnection;
|
||||
import io.smallrye.mutiny.Uni;
|
||||
|
||||
public class SSCardboard {
|
||||
|
||||
public static Uni<Void> sendCardboard(WebSocketConnection connection, CardboardEntity cardboardEntity) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendCardboard", cardboardEntity);
|
||||
public static void sendCardboard(WebSocketConnection connection, CardboardEntity cardboardEntity) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendCardboard", cardboardEntity);
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,33 +5,32 @@ import fr.titionfire.ffsaf.domain.entity.TreeEntity;
|
||||
import fr.titionfire.ffsaf.ws.CompetitionWS;
|
||||
import fr.titionfire.ffsaf.ws.recv.RCategorie;
|
||||
import io.quarkus.websockets.next.WebSocketConnection;
|
||||
import io.smallrye.mutiny.Uni;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class SSCategorie {
|
||||
|
||||
public static Uni<Void> sendAddCategory(WebSocketConnection connection, CategoryModel category) {
|
||||
return SSCategorie.sendAddCategory(connection, RCategorie.JustCategorie.from(category));
|
||||
public static void sendAddCategory(WebSocketConnection connection, CategoryModel category) {
|
||||
SSCategorie.sendAddCategory(connection, RCategorie.JustCategorie.from(category));
|
||||
}
|
||||
|
||||
public static Uni<Void> sendAddCategory(WebSocketConnection connection, RCategorie.JustCategorie justCategorie) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendAddCategory", justCategorie);
|
||||
public static void sendAddCategory(WebSocketConnection connection, RCategorie.JustCategorie justCategorie) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendAddCategory", justCategorie);
|
||||
}
|
||||
|
||||
public static Uni<Void> sendCategory(WebSocketConnection connection, CategoryModel category) {
|
||||
return SSCategorie.sendCategory(connection, RCategorie.JustCategorie.from(category));
|
||||
public static void sendCategory(WebSocketConnection connection, CategoryModel category) {
|
||||
SSCategorie.sendCategory(connection, RCategorie.JustCategorie.from(category));
|
||||
}
|
||||
|
||||
public static Uni<Void> sendCategory(WebSocketConnection connection, RCategorie.JustCategorie justCategorie) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendCategory", justCategorie);
|
||||
public static void sendCategory(WebSocketConnection connection, RCategorie.JustCategorie justCategorie) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendCategory", justCategorie);
|
||||
}
|
||||
|
||||
public static Uni<Void> sendTreeCategory(WebSocketConnection connection, List<TreeEntity> treeEntities) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendTreeCategory", treeEntities);
|
||||
public static void sendTreeCategory(WebSocketConnection connection, List<TreeEntity> treeEntities) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendTreeCategory", treeEntities);
|
||||
}
|
||||
|
||||
public static Uni<?> sendDelCategory(WebSocketConnection connection, Long id) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendDelCategory", id);
|
||||
public static void sendDelCategory(WebSocketConnection connection, Long id) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendDelCategory", id);
|
||||
}
|
||||
}
|
||||
|
||||
@ -4,29 +4,28 @@ import fr.titionfire.ffsaf.domain.entity.MatchEntity;
|
||||
import fr.titionfire.ffsaf.ws.CompetitionWS;
|
||||
import fr.titionfire.ffsaf.ws.recv.RMatch;
|
||||
import io.quarkus.websockets.next.WebSocketConnection;
|
||||
import io.smallrye.mutiny.Uni;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class SSMatch {
|
||||
|
||||
public static Uni<Void> sendMatch(WebSocketConnection connection, MatchEntity matchEntity) {
|
||||
return SSMatch.sendMatch(connection, List.of(matchEntity));
|
||||
public static void sendMatch(WebSocketConnection connection, MatchEntity matchEntity) {
|
||||
SSMatch.sendMatch(connection, List.of(matchEntity));
|
||||
}
|
||||
|
||||
public static Uni<Void> sendMatch(WebSocketConnection connection, List<MatchEntity> matchEntities) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendMatch", matchEntities);
|
||||
public static void sendMatch(WebSocketConnection connection, List<MatchEntity> matchEntities) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendMatch", matchEntities);
|
||||
}
|
||||
|
||||
public static Uni<Void> sendMatchOrder(WebSocketConnection connection, RMatch.MatchOrder matchOrder) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendMatchOrder", matchOrder);
|
||||
public static void sendMatchOrder(WebSocketConnection connection, RMatch.MatchOrder matchOrder) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendMatchOrder", matchOrder);
|
||||
}
|
||||
|
||||
public static Uni<Void> sendDeleteMatch(WebSocketConnection connection, Long l) {
|
||||
return SSMatch.sendDeleteMatch(connection, List.of(l));
|
||||
public static void sendDeleteMatch(WebSocketConnection connection, Long l) {
|
||||
SSMatch.sendDeleteMatch(connection, List.of(l));
|
||||
}
|
||||
|
||||
public static Uni<Void> sendDeleteMatch(WebSocketConnection connection, List<Long> longs) {
|
||||
return CompetitionWS.sendNotifyToOtherEditor(connection, "sendDeleteMatch", longs);
|
||||
public static void sendDeleteMatch(WebSocketConnection connection, List<Long> longs) {
|
||||
CompetitionWS.sendNotifyToOtherEditor(connection, "sendDeleteMatch", longs);
|
||||
}
|
||||
}
|
||||
|
||||
@ -8,6 +8,7 @@ quarkus.hibernate-orm.database.generation=update
|
||||
quarkus.hibernate-orm.physical-naming-strategy=fr.titionfire.ffsaf.data.SafcaNamingStrategy
|
||||
|
||||
quarkus.hibernate-orm.dialect=fr.titionfire.ffsaf.data.CustomPostgreSQLDialect
|
||||
quarkus.datasource.jdbc.reactive.max-size=40
|
||||
|
||||
quarkus.http.cors.enabled=true
|
||||
quarkus.quartz.start-mode=forced
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user