All Downloads are FREE. Search and download functionalities are using the official Maven repository.

net.intelie.live.plugins.messenger.chat.MessagesManager Maven / Gradle / Ivy

The newest version!
package net.intelie.live.plugins.messenger.chat;

import net.intelie.live.*;
import net.intelie.live.EventMap;
import net.intelie.live.plugins.feed.api.FeedDef;
import net.intelie.live.plugins.messenger.data.MessageSanitizer;
import net.intelie.live.plugins.messenger.data.RoomData;
import net.intelie.live.plugins.messenger.data.UserData;
import net.intelie.live.plugins.messenger.data.UserMessage;
import net.intelie.pipes.Property;
import net.intelie.pipes.filters.TermFilter;
import net.intelie.pipes.util.Escapes;
import net.intelie.pipes.util.Preconditions;

import java.util.*;

import static net.intelie.live.plugins.messenger.chat.EventUtils.fromEvent;
import static net.intelie.live.plugins.messenger.chat.EventUtils.toEvent;
import static net.intelie.live.plugins.messenger.chat.MessengerConstants.MESSENGER_EVENT_SRC;

public class MessagesManager {
    public static final String MESSAGE = "__message";
    static final String MESSAGE_NOT_FOUND = "Message was not found";
    private static final List INDEX_FIELDS = Collections.singletonList(Event.TIMESTAMP);
    private final Live live;
    private final EventLobby lobby;
    private final LoggedUser user;
    private final Property uidProperty;
    private final MessageSanitizer sanitizer;

    public MessagesManager(Live live) throws Exception {
        this.live = live;
        this.lobby = live.engine().getEventLobby();
        this.user = live.auth().getLoggedUser();
        this.uidProperty = live.pipes().compiler().getContext().property("uid");
        this.sanitizer = new MessageSanitizer();

        live.index().registerIndex(new IndexDef(MESSAGE, INDEX_FIELDS));
        live.index().registerIndex(new IndexDef(MESSAGE, "uid"));
        live.index().registerIndex(new IndexDef(MESSAGE, "createdAt", "room.id"));
    }

    private static Map toEventOverWrite(UserMessage message) {
        Map map = toEvent(message);
        map.put(Event.OVERWRITE, Collections.singletonList("uid"));
        return map;
    }

    private static void checkAuthorPermission(boolean allowDifferentAuthor, Integer authorId, Integer userId) {
        Preconditions.checkArgument(allowDifferentAuthor || Objects.equals(authorId, userId),
                "User#%s is trying to update message from User#%s. Not authorized!",
                userId, authorId);
    }

    public UserMessage send(String roomId, String message) {
        UserDef user = this.user.getUser();
        String timeZone = this.user.getTimeZone();
        String uid = UUID.randomUUID().toString().replace("-", "");
        UserData author = new UserData(user.getId(), user.getDisplayName());
        RoomData room = new RoomData(roomId);
        UserMessage userMessage = new UserMessage(uid, room, author, this.sanitizer.sanitize(message), timeZone);
        lobby.enter(MESSAGE, MESSENGER_EVENT_SRC, toEvent(userMessage));
        return userMessage;
    }

    public FeedDef.FeedItem feedItem(String roomId) {
        FeedDef.FeedItem item = feedItem();
        item.setFilter("room->id!:" + Escapes.formatString(roomId));
        return item;
    }

    public FeedDef.FeedItem feedItem() {
        FeedDef.FeedItem item = new FeedDef.FeedItem();
        item.setType(MESSAGE);
        item.setTimestamp("createdAt");
        return item;
    }

    public UserMessage update(UserMessage message, boolean allowDifferentAuthor, Integer userId) throws Exception {
        Preconditions.checkArgument(message.getUid() != null, "Message must have a unique id.");
        UserMessage oldData = updateQueryIterator(message);
        if (oldData == null) {
            throw new Exception(MESSAGE_NOT_FOUND);
        }
        checkAuthorPermission(allowDifferentAuthor, oldData.getAuthor().getId(), userId);
        oldData.updateFrom(message, this.sanitizer);
        live.engine().getEventLobby().enter(MESSAGE, MESSENGER_EVENT_SRC, toEventOverWrite(oldData));
        return oldData;
    }

    public UserMessage deleteById(String messageId, boolean allowDifferentAuthor, Integer userId) throws Exception {
        try (EventIterator it = getEventIterator(messageId, true)) {
            if (!it.moveNext()) {
                throw new Exception(MESSAGE_NOT_FOUND);
            }
            Event ev = it.current();
            UserMessage oldData = fromEvent(ev, UserMessage.class);
            checkAuthorPermission(allowDifferentAuthor, oldData.getAuthor().getId(), userId);
            it.delete();

            EventMap builder = ev.extend();
            builder.put(Event.TYPE, MESSAGE);
            builder.put("__delete", Collections.singletonList("uid"));
            builder.put(Event.SKIP_STORAGE, true);
            live.engine().getEventLobby().enter(Collections.singletonList(new Event(builder)));

            return oldData;
        }
    }

    private EventIterator getEventIterator(String messageId, boolean delete) throws Exception {
        TermFilter filter = TermFilter.literal(uidProperty, messageId);
        return live.engine().getMainStorage().query(new StorageQuery(MESSAGE).withWhere(filter).withLimit(1), 0, Long.MAX_VALUE, new StorageQueryOptions(false, delete));
    }

    private UserMessage updateQueryIterator(UserMessage message) throws Exception {
        try (EventIterator it = getEventIterator(message.getUid(), false)) {
            return it.moveNext() ? fromEvent(it.current(), UserMessage.class) : null;
        }
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy