Почта v2: ReceiveOutcomingMessage без авторизации и атомарная вставка пары

This commit is contained in:
AidarKC
2026-05-02 16:46:22 +03:00
parent e73328461e
commit b7e6cf7437
6 changed files with 123 additions and 18 deletions
@@ -143,6 +143,7 @@ public final class JsonHandlerRegistry {
Map.entry("SendTestWebPush", new Net_SendTestWebPush_Handler()),
Map.entry("SendDirectMessage", new Net_SendDirectMessage_Handler()),
Map.entry("SendMessagePair", new Net_SendMessagePair_Handler()),
Map.entry("ReceiveOutcomingMessage", new Net_SendMessagePair_Handler()),
Map.entry("ReceiveIncomingMessage", new Net_ReceiveIncomingMessage_Handler()),
Map.entry("AckIncomingMessage", new Net_AckIncomingMessage_Handler()),
Map.entry("AckSessionDelivery", new Net_AckSessionDelivery_Handler()),
@@ -199,6 +200,7 @@ public final class JsonHandlerRegistry {
Map.entry("SendTestWebPush", Net_SendTestWebPush_Request.class),
Map.entry("SendDirectMessage", Net_SendDirectMessage_Request.class),
Map.entry("SendMessagePair", Net_SendMessagePair_Request.class),
Map.entry("ReceiveOutcomingMessage", Net_SendMessagePair_Request.class),
Map.entry("ReceiveIncomingMessage", Net_ReceiveIncomingMessage_Request.class),
Map.entry("AckIncomingMessage", Net_AckIncomingMessage_Request.class),
Map.entry("AckSessionDelivery", Net_AckSessionDelivery_Request.class),
@@ -8,15 +8,13 @@ import server.logic.ws_protocol.JSON.messages.entyties.Net_SendMessagePair_Reque
import server.logic.ws_protocol.JSON.messages.entyties.Net_SendMessagePair_Response;
import server.logic.ws_protocol.JSON.utils.NetExceptionResponseFactory;
import server.logic.ws_protocol.WireCodes;
import shine.db.dao.SignedMessagesV2DAO;
import shine.db.entities.SignedMessageV2Entry;
public class Net_SendMessagePair_Handler implements JsonMessageHandler {
@Override
public Net_Response handle(Net_Request baseRequest, ConnectionContext ctx) throws Exception {
Net_SendMessagePair_Request req = (Net_SendMessagePair_Request) baseRequest;
if (ctx == null || !ctx.isAuthenticatedUser()) {
return NetExceptionResponseFactory.error(req, WireCodes.Status.UNVERIFIED, "NOT_AUTHENTICATED", "Требуется авторизация");
}
if (isBlank(req.getIncomingBlobB64()) || isBlank(req.getOutgoingBlobB64())) {
return NetExceptionResponseFactory.error(req, WireCodes.Status.BAD_REQUEST, "BAD_FIELDS", "incomingBlobB64/outgoingBlobB64 обязательны");
}
@@ -31,10 +29,6 @@ public class Net_SendMessagePair_Handler implements JsonMessageHandler {
return NetExceptionResponseFactory.error(req, WireCodes.Status.BAD_REQUEST, ex.getMessage(), "Некорректный формат пары сообщений");
}
if (!incoming.fromLogin.equalsIgnoreCase(ctx.getLogin())) {
return NetExceptionResponseFactory.error(req, WireCodes.Status.UNVERIFIED, "SENDER_MISMATCH", "fromLogin должен совпадать с авторизованной сессией");
}
try {
SignedMessagesCore.verifyUsersAndSignature(incoming);
SignedMessagesCore.verifyUsersAndSignature(outgoing);
@@ -47,23 +41,27 @@ public class Net_SendMessagePair_Handler implements JsonMessageHandler {
SignedMessageV2Entry incomingEntry;
SignedMessageV2Entry outgoingEntry;
try {
incomingEntry = SignedMessagesCore.toEntry(incoming, "SendMessagePair", ctx.getSessionId());
outgoingEntry = SignedMessagesCore.toEntry(outgoing, "SendMessagePair", ctx.getSessionId());
String sourceApi = "ReceiveOutcomingMessage";
String originSessionId = (ctx != null && !isBlank(ctx.getSessionId())) ? ctx.getSessionId() : null;
incomingEntry = SignedMessagesCore.toEntry(incoming, sourceApi, originSessionId);
outgoingEntry = SignedMessagesCore.toEntry(outgoing, sourceApi, originSessionId);
} catch (IllegalArgumentException ex) {
return NetExceptionResponseFactory.error(req, WireCodes.Status.BAD_REQUEST, ex.getMessage(), "Некорректный payload подтверждения");
}
boolean incomingInserted = SignedMessagesCore.saveIfAbsent(incomingEntry);
boolean outgoingInserted = SignedMessagesCore.saveIfAbsent(outgoingEntry);
boolean pairInserted = SignedMessagesV2DAO.getInstance().insertPairBothOrNothing(incomingEntry, outgoingEntry);
SignedMessagesRealtime.DeliveryCounters inCounters = new SignedMessagesRealtime.DeliveryCounters();
if (incomingInserted) {
if (pairInserted) {
inCounters = SignedMessagesRealtime.deliverToTargetSessions(incomingEntry, null);
}
String excludeSessionId = outgoingEntry.getTargetLogin().equalsIgnoreCase(ctx.getLogin()) ? ctx.getSessionId() : null;
String excludeSessionId = null;
if (ctx != null && !isBlank(ctx.getLogin()) && outgoingEntry.getTargetLogin().equalsIgnoreCase(ctx.getLogin())) {
excludeSessionId = ctx.getSessionId();
}
SignedMessagesRealtime.DeliveryCounters outCounters = new SignedMessagesRealtime.DeliveryCounters();
if (outgoingInserted) {
if (pairInserted) {
outCounters = SignedMessagesRealtime.deliverToTargetSessions(outgoingEntry, excludeSessionId);
}