Implement a better Sone Rescue Mode.
[Sone.git] / src / main / java / net / pterodactylus / sone / web / WebInterface.java
index 8eb0122..6807b35 100644 (file)
@@ -100,6 +100,7 @@ import net.pterodactylus.util.cache.CacheItem;
 import net.pterodactylus.util.cache.DefaultCacheItem;
 import net.pterodactylus.util.cache.MemoryCache;
 import net.pterodactylus.util.cache.ValueRetriever;
+import net.pterodactylus.util.collection.SetBuilder;
 import net.pterodactylus.util.filter.Filters;
 import net.pterodactylus.util.logging.Logging;
 import net.pterodactylus.util.notify.Notification;
@@ -168,6 +169,12 @@ public class WebInterface implements CoreListener {
        /** The “new reply” notification. */
        private final ListNotification<Reply> newReplyNotification;
 
+       /** The invisible “local post” notification. */
+       private final ListNotification<Post> localPostNotification;
+
+       /** The invisible “local reply” notification. */
+       private final ListNotification<Reply> localReplyNotification;
+
        /** The “you have been mentioned” notification. */
        private final ListNotification<Post> mentionNotification;
 
@@ -196,7 +203,7 @@ public class WebInterface implements CoreListener {
        public WebInterface(SonePlugin sonePlugin) {
                this.sonePlugin = sonePlugin;
                formPassword = sonePlugin.pluginRespirator().getToadletContainer().getFormPassword();
-               soneTextParser = new SoneTextParser(getCore());
+               soneTextParser = new SoneTextParser(getCore(), getCore());
 
                templateContextFactory = new TemplateContextFactory();
                templateContextFactory.addAccessor(Object.class, new ReflectionAccessor());
@@ -236,9 +243,15 @@ public class WebInterface implements CoreListener {
                Template newPostNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newPostNotification.html"));
                newPostNotification = new ListNotification<Post>("new-post-notification", "posts", newPostNotificationTemplate, false);
 
+               Template localPostNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newPostNotification.html"));
+               localPostNotification = new ListNotification<Post>("local-post-notification", "posts", localPostNotificationTemplate, false);
+
                Template newReplyNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newReplyNotification.html"));
                newReplyNotification = new ListNotification<Reply>("new-reply-notification", "replies", newReplyNotificationTemplate, false);
 
+               Template localReplyNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newReplyNotification.html"));
+               localReplyNotification = new ListNotification<Reply>("local-reply-notification", "replies", localReplyNotificationTemplate, false);
+
                Template mentionNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/mentionNotification.html"));
                mentionNotification = new ListNotification<Post>("mention-notification", "posts", mentionNotificationTemplate, false);
 
@@ -420,7 +433,7 @@ public class WebInterface implements CoreListener {
         * @return The new posts
         */
        public Set<Post> getNewPosts() {
-               return new HashSet<Post>(newPostNotification.getElements());
+               return new SetBuilder<Post>().addAll(newPostNotification.getElements()).addAll(localPostNotification.getElements()).get();
        }
 
        /**
@@ -430,7 +443,7 @@ public class WebInterface implements CoreListener {
         * @return The new replies
         */
        public Set<Reply> getNewReplies() {
-               return new HashSet<Reply>(newReplyNotification.getElements());
+               return new SetBuilder<Reply>().addAll(newReplyNotification.getElements()).addAll(localReplyNotification.getElements()).get();
        }
 
        /**
@@ -555,6 +568,7 @@ public class WebInterface implements CoreListener {
                Template deleteSoneTemplate = TemplateParser.parse(createReader("/templates/deleteSone.html"));
                Template noPermissionTemplate = TemplateParser.parse(createReader("/templates/noPermission.html"));
                Template optionsTemplate = TemplateParser.parse(createReader("/templates/options.html"));
+               Template rescueTemplate = TemplateParser.parse(createReader("/templates/rescue.html"));
                Template aboutTemplate = TemplateParser.parse(createReader("/templates/about.html"));
                Template invalidTemplate = TemplateParser.parse(createReader("/templates/invalid.html"));
                Template postTemplate = TemplateParser.parse(createReader("/templates/include/viewPost.html"));
@@ -593,6 +607,7 @@ public class WebInterface implements CoreListener {
                pageToadlets.add(pageToadletFactory.createPageToadlet(new LoginPage(loginTemplate, this), "Login"));
                pageToadlets.add(pageToadletFactory.createPageToadlet(new LogoutPage(emptyTemplate, this), "Logout"));
                pageToadlets.add(pageToadletFactory.createPageToadlet(new OptionsPage(optionsTemplate, this), "Options"));
+               pageToadlets.add(pageToadletFactory.createPageToadlet(new RescuePage(rescueTemplate, this), "Rescue"));
                pageToadlets.add(pageToadletFactory.createPageToadlet(new AboutPage(aboutTemplate, this, SonePlugin.VERSION), "About"));
                pageToadlets.add(pageToadletFactory.createPageToadlet(new SoneTemplatePage("noPermission.html", noPermissionTemplate, "Page.NoPermission.Title", this)));
                pageToadlets.add(pageToadletFactory.createPageToadlet(new DismissNotificationPage(emptyTemplate, this)));
@@ -668,6 +683,15 @@ public class WebInterface implements CoreListener {
                }
        }
 
+       /**
+        * Returns all {@link Core#isLocalSone(Sone) local Sone}s that are
+        * referenced by {@link SonePart}s in the given text (after parsing it using
+        * {@link SoneTextParser}).
+        *
+        * @param text
+        *            The text to parse
+        * @return All mentioned local Sones
+        */
        private Set<Sone> getMentionedSones(String text) {
                /* we need no context to find mentioned Sones. */
                Set<Sone> mentionedSones = new HashSet<Sone>();
@@ -722,10 +746,15 @@ public class WebInterface implements CoreListener {
         */
        @Override
        public void newPostFound(Post post) {
-               newPostNotification.add(post);
+               boolean isLocal = getCore().isLocalSone(post.getSone());
+               if (isLocal) {
+                       localPostNotification.add(post);
+               } else {
+                       newPostNotification.add(post);
+               }
                if (!hasFirstStartNotification()) {
-                       notificationManager.addNotification(newPostNotification);
-                       if (!getMentionedSones(post.getText()).isEmpty()) {
+                       notificationManager.addNotification(isLocal ? localPostNotification : newPostNotification);
+                       if (!getMentionedSones(post.getText()).isEmpty() && !isLocal) {
                                mentionNotification.add(post);
                                notificationManager.addNotification(mentionNotification);
                        }
@@ -739,13 +768,15 @@ public class WebInterface implements CoreListener {
         */
        @Override
        public void newReplyFound(Reply reply) {
-               if (reply.getPost().getSone() == null) {
-                       return;
+               boolean isLocal = getCore().isLocalSone(reply.getSone());
+               if (isLocal) {
+                       localReplyNotification.add(reply);
+               } else {
+                       newReplyNotification.add(reply);
                }
-               newReplyNotification.add(reply);
                if (!hasFirstStartNotification()) {
-                       notificationManager.addNotification(newReplyNotification);
-                       if (!getMentionedSones(reply.getText()).isEmpty()) {
+                       notificationManager.addNotification(isLocal ? localReplyNotification : newReplyNotification);
+                       if (!getMentionedSones(reply.getText()).isEmpty() && !isLocal) {
                                mentionNotification.add(reply.getPost());
                                notificationManager.addNotification(mentionNotification);
                        }
@@ -768,6 +799,7 @@ public class WebInterface implements CoreListener {
        @Override
        public void markPostKnown(Post post) {
                newPostNotification.remove(post);
+               localPostNotification.remove(post);
                mentionNotification.remove(post);
        }
 
@@ -777,6 +809,7 @@ public class WebInterface implements CoreListener {
        @Override
        public void markReplyKnown(Reply reply) {
                newReplyNotification.remove(reply);
+               localReplyNotification.remove(reply);
                mentionNotification.remove(reply.getPost());
        }
 
@@ -794,6 +827,7 @@ public class WebInterface implements CoreListener {
        @Override
        public void postRemoved(Post post) {
                newPostNotification.remove(post);
+               localPostNotification.remove(post);
        }
 
        /**
@@ -802,6 +836,7 @@ public class WebInterface implements CoreListener {
        @Override
        public void replyRemoved(Reply reply) {
                newReplyNotification.remove(reply);
+               localReplyNotification.remove(reply);
        }
 
        /**