X-Git-Url: https://git.pterodactylus.net/?p=Sone.git;a=blobdiff_plain;f=src%2Fmain%2Fjava%2Fnet%2Fpterodactylus%2Fsone%2Fweb%2FWebInterface.java;h=c2bb1c8ebe93f2c015a9596787ba798d701479af;hp=6807b35c4a93aab0621b8b20b7fa7324af487ee1;hb=b3c3c6547d75c24d0f2646b1cdc02c51d5f0a3c0;hpb=bb2c8cb2d47a77bcef2d299ad4bf8e16f22a6198 diff --git a/src/main/java/net/pterodactylus/sone/web/WebInterface.java b/src/main/java/net/pterodactylus/sone/web/WebInterface.java index 6807b35..c2bb1c8 100644 --- a/src/main/java/net/pterodactylus/sone/web/WebInterface.java +++ b/src/main/java/net/pterodactylus/sone/web/WebInterface.java @@ -1,5 +1,5 @@ /* - * Sone - WebInterface.java - Copyright © 2010 David Roden + * Sone - WebInterface.java - Copyright © 2010–2012 David Roden * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -37,7 +37,11 @@ import java.util.logging.Logger; import net.pterodactylus.sone.core.Core; import net.pterodactylus.sone.core.CoreListener; +import net.pterodactylus.sone.data.Album; +import net.pterodactylus.sone.data.Image; import net.pterodactylus.sone.data.Post; +import net.pterodactylus.sone.data.PostReply; +import net.pterodactylus.sone.data.Profile; import net.pterodactylus.sone.data.Reply; import net.pterodactylus.sone.data.Sone; import net.pterodactylus.sone.freenet.L10nFilter; @@ -45,19 +49,24 @@ import net.pterodactylus.sone.freenet.wot.Identity; import net.pterodactylus.sone.freenet.wot.Trust; import net.pterodactylus.sone.main.SonePlugin; import net.pterodactylus.sone.notify.ListNotification; +import net.pterodactylus.sone.template.AlbumAccessor; import net.pterodactylus.sone.template.CollectionAccessor; import net.pterodactylus.sone.template.CssClassNameFilter; import net.pterodactylus.sone.template.HttpRequestAccessor; import net.pterodactylus.sone.template.IdentityAccessor; +import net.pterodactylus.sone.template.ImageAccessor; +import net.pterodactylus.sone.template.ImageLinkFilter; import net.pterodactylus.sone.template.JavascriptFilter; import net.pterodactylus.sone.template.ParserFilter; import net.pterodactylus.sone.template.PostAccessor; +import net.pterodactylus.sone.template.ProfileAccessor; import net.pterodactylus.sone.template.ReplyAccessor; import net.pterodactylus.sone.template.ReplyGroupFilter; import net.pterodactylus.sone.template.RequestChangeFilter; import net.pterodactylus.sone.template.SoneAccessor; import net.pterodactylus.sone.template.SubstringFilter; import net.pterodactylus.sone.template.TrustAccessor; +import net.pterodactylus.sone.template.UniqueElementFilter; import net.pterodactylus.sone.template.UnknownDateFilter; import net.pterodactylus.sone.text.Part; import net.pterodactylus.sone.text.SonePart; @@ -70,10 +79,12 @@ import net.pterodactylus.sone.web.ajax.DeleteProfileFieldAjaxPage; import net.pterodactylus.sone.web.ajax.DeleteReplyAjaxPage; import net.pterodactylus.sone.web.ajax.DismissNotificationAjaxPage; import net.pterodactylus.sone.web.ajax.DistrustAjaxPage; +import net.pterodactylus.sone.web.ajax.EditAlbumAjaxPage; +import net.pterodactylus.sone.web.ajax.EditImageAjaxPage; import net.pterodactylus.sone.web.ajax.EditProfileFieldAjaxPage; import net.pterodactylus.sone.web.ajax.FollowSoneAjaxPage; import net.pterodactylus.sone.web.ajax.GetLikesAjaxPage; -import net.pterodactylus.sone.web.ajax.GetNotificationAjaxPage; +import net.pterodactylus.sone.web.ajax.GetNotificationsAjaxPage; import net.pterodactylus.sone.web.ajax.GetPostAjaxPage; import net.pterodactylus.sone.web.ajax.GetReplyAjaxPage; import net.pterodactylus.sone.web.ajax.GetStatusAjaxPage; @@ -89,11 +100,9 @@ import net.pterodactylus.sone.web.ajax.UnfollowSoneAjaxPage; import net.pterodactylus.sone.web.ajax.UnlikeAjaxPage; import net.pterodactylus.sone.web.ajax.UnlockSoneAjaxPage; import net.pterodactylus.sone.web.ajax.UntrustAjaxPage; +import net.pterodactylus.sone.web.page.FreenetRequest; import net.pterodactylus.sone.web.page.PageToadlet; import net.pterodactylus.sone.web.page.PageToadletFactory; -import net.pterodactylus.sone.web.page.RedirectPage; -import net.pterodactylus.sone.web.page.StaticPage; -import net.pterodactylus.sone.web.page.TemplatePage; import net.pterodactylus.util.cache.Cache; import net.pterodactylus.util.cache.CacheException; import net.pterodactylus.util.cache.CacheItem; @@ -101,7 +110,7 @@ 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.collection.filter.Filters; import net.pterodactylus.util.logging.Logging; import net.pterodactylus.util.notify.Notification; import net.pterodactylus.util.notify.NotificationManager; @@ -112,6 +121,8 @@ import net.pterodactylus.util.template.DateFilter; import net.pterodactylus.util.template.FormatFilter; import net.pterodactylus.util.template.HtmlFilter; import net.pterodactylus.util.template.MatchFilter; +import net.pterodactylus.util.template.ModFilter; +import net.pterodactylus.util.template.PaginationFilter; import net.pterodactylus.util.template.Provider; import net.pterodactylus.util.template.ReflectionAccessor; import net.pterodactylus.util.template.ReplaceFilter; @@ -124,6 +135,9 @@ import net.pterodactylus.util.template.TemplateParser; import net.pterodactylus.util.template.XmlFilter; import net.pterodactylus.util.thread.Ticker; import net.pterodactylus.util.version.Version; +import net.pterodactylus.util.web.RedirectPage; +import net.pterodactylus.util.web.StaticPage; +import net.pterodactylus.util.web.TemplatePage; import freenet.clients.http.SessionManager; import freenet.clients.http.SessionManager.Session; import freenet.clients.http.ToadletContainer; @@ -160,6 +174,9 @@ public class WebInterface implements CoreListener { /** The Sone text parser. */ private final SoneTextParser soneTextParser; + /** The parser filter. */ + private final ParserFilter parserFilter; + /** The “new Sone” notification. */ private final ListNotification newSoneNotification; @@ -167,22 +184,19 @@ public class WebInterface implements CoreListener { private final ListNotification newPostNotification; /** The “new reply” notification. */ - private final ListNotification newReplyNotification; + private final ListNotification newReplyNotification; /** The invisible “local post” notification. */ private final ListNotification localPostNotification; /** The invisible “local reply” notification. */ - private final ListNotification localReplyNotification; + private final ListNotification localReplyNotification; /** The “you have been mentioned” notification. */ private final ListNotification mentionNotification; - /** The “rescuing Sone” notification. */ - private final ListNotification rescuingSonesNotification; - - /** The “Sone rescued” notification. */ - private final ListNotification sonesRescuedNotification; + /** Notifications for sone inserts. */ + private final Map soneInsertNotifications = new HashMap(); /** Sone locked notification ticker objects. */ private final Map lockedSonesTickerObjects = Collections.synchronizedMap(new HashMap()); @@ -193,6 +207,15 @@ public class WebInterface implements CoreListener { /** The “new version” notification. */ private final TemplateNotification newVersionNotification; + /** The “inserting images” notification. */ + private final ListNotification insertingImagesNotification; + + /** The “inserted images” notification. */ + private final ListNotification insertedImagesNotification; + + /** The “image insert failed” notification. */ + private final ListNotification imageInsertFailedNotification; + /** * Creates a new web interface. * @@ -211,26 +234,33 @@ public class WebInterface implements CoreListener { templateContextFactory.addAccessor(Sone.class, new SoneAccessor(getCore())); templateContextFactory.addAccessor(Post.class, new PostAccessor(getCore())); templateContextFactory.addAccessor(Reply.class, new ReplyAccessor(getCore())); + templateContextFactory.addAccessor(Album.class, new AlbumAccessor()); + templateContextFactory.addAccessor(Image.class, new ImageAccessor()); templateContextFactory.addAccessor(Identity.class, new IdentityAccessor(getCore())); templateContextFactory.addAccessor(Trust.class, new TrustAccessor()); templateContextFactory.addAccessor(HTTPRequest.class, new HttpRequestAccessor()); + templateContextFactory.addAccessor(Profile.class, new ProfileAccessor(getCore())); templateContextFactory.addFilter("date", new DateFilter()); templateContextFactory.addFilter("html", new HtmlFilter()); templateContextFactory.addFilter("replace", new ReplaceFilter()); templateContextFactory.addFilter("store", new StoreFilter()); - templateContextFactory.addFilter("l10n", new L10nFilter(getL10n())); + templateContextFactory.addFilter("l10n", new L10nFilter(this)); templateContextFactory.addFilter("substring", new SubstringFilter()); templateContextFactory.addFilter("xml", new XmlFilter()); templateContextFactory.addFilter("change", new RequestChangeFilter()); templateContextFactory.addFilter("match", new MatchFilter()); templateContextFactory.addFilter("css", new CssClassNameFilter()); templateContextFactory.addFilter("js", new JavascriptFilter()); - templateContextFactory.addFilter("parse", new ParserFilter(getCore(), templateContextFactory, soneTextParser)); + templateContextFactory.addFilter("parse", parserFilter = new ParserFilter(getCore(), templateContextFactory, soneTextParser)); templateContextFactory.addFilter("unknown", new UnknownDateFilter(getL10n(), "View.Sone.Text.UnknownDate")); templateContextFactory.addFilter("format", new FormatFilter()); templateContextFactory.addFilter("sort", new CollectionSortFilter()); + templateContextFactory.addFilter("image-link", new ImageLinkFilter(getCore(), templateContextFactory)); templateContextFactory.addFilter("replyGroup", new ReplyGroupFilter()); templateContextFactory.addFilter("in", new ContainsFilter()); + templateContextFactory.addFilter("unique", new UniqueElementFilter()); + templateContextFactory.addFilter("mod", new ModFilter()); + templateContextFactory.addFilter("paginate", new PaginationFilter()); templateContextFactory.addProvider(Provider.TEMPLATE_CONTEXT_PROVIDER); templateContextFactory.addProvider(new ClassPathTemplateProvider()); templateContextFactory.addTemplateObject("webInterface", this); @@ -247,25 +277,28 @@ public class WebInterface implements CoreListener { localPostNotification = new ListNotification("local-post-notification", "posts", localPostNotificationTemplate, false); Template newReplyNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newReplyNotification.html")); - newReplyNotification = new ListNotification("new-reply-notification", "replies", newReplyNotificationTemplate, false); + newReplyNotification = new ListNotification("new-reply-notification", "replies", newReplyNotificationTemplate, false); Template localReplyNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/newReplyNotification.html")); - localReplyNotification = new ListNotification("local-reply-notification", "replies", localReplyNotificationTemplate, false); + localReplyNotification = new ListNotification("local-reply-notification", "replies", localReplyNotificationTemplate, false); Template mentionNotificationTemplate = TemplateParser.parse(createReader("/templates/notify/mentionNotification.html")); mentionNotification = new ListNotification("mention-notification", "posts", mentionNotificationTemplate, false); - Template rescuingSonesTemplate = TemplateParser.parse(createReader("/templates/notify/rescuingSonesNotification.html")); - rescuingSonesNotification = new ListNotification("sones-being-rescued-notification", "sones", rescuingSonesTemplate); - - Template sonesRescuedTemplate = TemplateParser.parse(createReader("/templates/notify/sonesRescuedNotification.html")); - sonesRescuedNotification = new ListNotification("sones-rescued-notification", "sones", sonesRescuedTemplate); - Template lockedSonesTemplate = TemplateParser.parse(createReader("/templates/notify/lockedSonesNotification.html")); lockedSonesNotification = new ListNotification("sones-locked-notification", "sones", lockedSonesTemplate); Template newVersionTemplate = TemplateParser.parse(createReader("/templates/notify/newVersionNotification.html")); newVersionNotification = new TemplateNotification("new-version-notification", newVersionTemplate); + + Template insertingImagesTemplate = TemplateParser.parse(createReader("/templates/notify/inserting-images-notification.html")); + insertingImagesNotification = new ListNotification("inserting-images-notification", "images", insertingImagesTemplate); + + Template insertedImagesTemplate = TemplateParser.parse(createReader("/templates/notify/inserted-images-notification.html")); + insertedImagesNotification = new ListNotification("inserted-images-notification", "images", insertedImagesTemplate); + + Template imageInsertFailedTemplate = TemplateParser.parse(createReader("/templates/notify/image-insert-failed-notification.html")); + imageInsertFailedNotification = new ListNotification("image-insert-failed-notification", "images", imageInsertFailedTemplate); } // @@ -442,8 +475,8 @@ public class WebInterface implements CoreListener { * * @return The new replies */ - public Set getNewReplies() { - return new SetBuilder().addAll(newReplyNotification.getElements()).addAll(localReplyNotification.getElements()).get(); + public Set getNewReplies() { + return new SetBuilder().addAll(newReplyNotification.getElements()).addAll(localReplyNotification.getElements()).get(); } /** @@ -552,6 +585,7 @@ public class WebInterface implements CoreListener { Template emptyTemplate = TemplateParser.parse(new StringReader("")); Template loginTemplate = TemplateParser.parse(createReader("/templates/login.html")); Template indexTemplate = TemplateParser.parse(createReader("/templates/index.html")); + Template newTemplate = TemplateParser.parse(createReader("/templates/new.html")); Template knownSonesTemplate = TemplateParser.parse(createReader("/templates/knownSones.html")); Template createSoneTemplate = TemplateParser.parse(createReader("/templates/createSone.html")); Template createPostTemplate = TemplateParser.parse(createReader("/templates/createPost.html")); @@ -566,6 +600,10 @@ public class WebInterface implements CoreListener { Template deletePostTemplate = TemplateParser.parse(createReader("/templates/deletePost.html")); Template deleteReplyTemplate = TemplateParser.parse(createReader("/templates/deleteReply.html")); Template deleteSoneTemplate = TemplateParser.parse(createReader("/templates/deleteSone.html")); + Template imageBrowserTemplate = TemplateParser.parse(createReader("/templates/imageBrowser.html")); + Template createAlbumTemplate = TemplateParser.parse(createReader("/templates/createAlbum.html")); + Template deleteAlbumTemplate = TemplateParser.parse(createReader("/templates/deleteAlbum.html")); + Template deleteImageTemplate = TemplateParser.parse(createReader("/templates/deleteImage.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")); @@ -576,8 +614,9 @@ public class WebInterface implements CoreListener { Template openSearchTemplate = TemplateParser.parse(createReader("/templates/xml/OpenSearch.xml")); PageToadletFactory pageToadletFactory = new PageToadletFactory(sonePlugin.pluginRespirator().getHLSimpleClient(), "/Sone/"); - pageToadlets.add(pageToadletFactory.createPageToadlet(new RedirectPage("", "index.html"))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new RedirectPage("", "index.html"))); pageToadlets.add(pageToadletFactory.createPageToadlet(new IndexPage(indexTemplate, this), "Index")); + pageToadlets.add(pageToadletFactory.createPageToadlet(new NewPage(newTemplate, this), "New")); pageToadlets.add(pageToadletFactory.createPageToadlet(new CreateSonePage(createSoneTemplate, this), "CreateSone")); pageToadlets.add(pageToadletFactory.createPageToadlet(new KnownSonesPage(knownSonesTemplate, this), "KnownSones")); pageToadlets.add(pageToadletFactory.createPageToadlet(new EditProfilePage(editProfileTemplate, this), "EditProfile")); @@ -595,6 +634,13 @@ public class WebInterface implements CoreListener { pageToadlets.add(pageToadletFactory.createPageToadlet(new UnlockSonePage(emptyTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new FollowSonePage(emptyTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new UnfollowSonePage(emptyTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new ImageBrowserPage(imageBrowserTemplate, this), "ImageBrowser")); + pageToadlets.add(pageToadletFactory.createPageToadlet(new CreateAlbumPage(createAlbumTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new EditAlbumPage(emptyTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new DeleteAlbumPage(deleteAlbumTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new UploadImagePage(invalidTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new EditImagePage(emptyTemplate, this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new DeleteImagePage(deleteImageTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new TrustPage(emptyTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new DistrustPage(emptyTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new UntrustPage(emptyTemplate, this))); @@ -612,13 +658,14 @@ public class WebInterface implements CoreListener { pageToadlets.add(pageToadletFactory.createPageToadlet(new SoneTemplatePage("noPermission.html", noPermissionTemplate, "Page.NoPermission.Title", this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new DismissNotificationPage(emptyTemplate, this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new SoneTemplatePage("invalid.html", invalidTemplate, "Page.Invalid.Title", this))); - pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("css/", "/static/css/", "text/css"))); - pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("javascript/", "/static/javascript/", "text/javascript"))); - pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("images/", "/static/images/", "image/png"))); - pageToadlets.add(pageToadletFactory.createPageToadlet(new TemplatePage("OpenSearch.xml", "application/opensearchdescription+xml", templateContextFactory, openSearchTemplate))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("css/", "/static/css/", "text/css"))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("javascript/", "/static/javascript/", "text/javascript"))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new StaticPage("images/", "/static/images/", "image/png"))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new TemplatePage("OpenSearch.xml", "application/opensearchdescription+xml", templateContextFactory, openSearchTemplate))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new GetImagePage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new GetTranslationPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new GetStatusAjaxPage(this))); - pageToadlets.add(pageToadletFactory.createPageToadlet(new GetNotificationAjaxPage(this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new GetNotificationsAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new DismissNotificationAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new CreatePostAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new CreateReplyAjaxPage(this))); @@ -632,6 +679,8 @@ public class WebInterface implements CoreListener { pageToadlets.add(pageToadletFactory.createPageToadlet(new UnlockSoneAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new FollowSoneAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new UnfollowSoneAjaxPage(this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new EditAlbumAjaxPage(this))); + pageToadlets.add(pageToadletFactory.createPageToadlet(new EditImageAjaxPage(this, parserFilter))); pageToadlets.add(pageToadletFactory.createPageToadlet(new TrustAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new DistrustAjaxPage(this))); pageToadlets.add(pageToadletFactory.createPageToadlet(new UntrustAjaxPage(this))); @@ -645,11 +694,11 @@ public class WebInterface implements CoreListener { pageToadlets.add(pageToadletFactory.createPageToadlet(new MoveProfileFieldAjaxPage(this))); ToadletContainer toadletContainer = sonePlugin.pluginRespirator().getToadletContainer(); - toadletContainer.getPageMaker().addNavigationCategory("/Sone/index.html", "Navigation.Menu.Name", "Navigation.Menu.Tooltip", sonePlugin); + toadletContainer.getPageMaker().addNavigationCategory("/Sone/index.html", "Navigation.Menu.Sone.Name", "Navigation.Menu.Sone.Tooltip", sonePlugin); for (PageToadlet toadlet : pageToadlets) { String menuName = toadlet.getMenuName(); if (menuName != null) { - toadletContainer.register(toadlet, "Navigation.Menu.Name", toadlet.path(), true, "Navigation.Menu.Item." + menuName + ".Name", "Navigation.Menu.Item." + menuName + ".Tooltip", false, toadlet); + toadletContainer.register(toadlet, "Navigation.Menu.Sone.Name", toadlet.path(), true, "Navigation.Menu.Sone.Item." + menuName + ".Name", "Navigation.Menu.Sone.Item." + menuName + ".Tooltip", false, toadlet); } else { toadletContainer.register(toadlet, null, toadlet.path(), true, false); } @@ -664,7 +713,7 @@ public class WebInterface implements CoreListener { for (PageToadlet pageToadlet : pageToadlets) { toadletContainer.unregister(pageToadlet); } - toadletContainer.getPageMaker().removeNavigationCategory("Navigation.Menu.Name"); + toadletContainer.getPageMaker().removeNavigationCategory("Navigation.Menu.Sone.Name"); } /** @@ -702,33 +751,35 @@ public class WebInterface implements CoreListener { } } } catch (IOException ioe1) { - logger.log(Level.WARNING, "Could not parse post text: " + text, ioe1); + logger.log(Level.WARNING, String.format("Could not parse post text: %s", text), ioe1); } return Filters.filteredSet(mentionedSones, Sone.LOCAL_SONE_FILTER); } - // - // CORELISTENER METHODS - // - /** - * {@inheritDoc} + * Returns the Sone insert notification for the given Sone. If no + * notification for the given Sone exists, a new notification is created and + * cached. + * + * @param sone + * The Sone to get the insert notification for + * @return The Sone insert notification */ - @Override - public void rescuingSone(Sone sone) { - rescuingSonesNotification.add(sone); - notificationManager.addNotification(rescuingSonesNotification); + private TemplateNotification getSoneInsertNotification(Sone sone) { + synchronized (soneInsertNotifications) { + TemplateNotification templateNotification = soneInsertNotifications.get(sone); + if (templateNotification == null) { + templateNotification = new TemplateNotification(TemplateParser.parse(createReader("/templates/notify/soneInsertNotification.html"))); + templateNotification.set("insertSone", sone); + soneInsertNotifications.put(sone, templateNotification); + } + return templateNotification; + } } - /** - * {@inheritDoc} - */ - @Override - public void rescuedSone(Sone sone) { - rescuingSonesNotification.remove(sone); - sonesRescuedNotification.add(sone); - notificationManager.addNotification(sonesRescuedNotification); - } + // + // CORELISTENER METHODS + // /** * {@inheritDoc} @@ -767,7 +818,7 @@ public class WebInterface implements CoreListener { * {@inheritDoc} */ @Override - public void newReplyFound(Reply reply) { + public void newReplyFound(PostReply reply) { boolean isLocal = getCore().isLocalSone(reply.getSone()); if (isLocal) { localReplyNotification.add(reply); @@ -776,7 +827,7 @@ public class WebInterface implements CoreListener { } if (!hasFirstStartNotification()) { notificationManager.addNotification(isLocal ? localReplyNotification : newReplyNotification); - if (!getMentionedSones(reply.getText()).isEmpty() && !isLocal) { + if (!getMentionedSones(reply.getText()).isEmpty() && !isLocal && (reply.getPost().getSone() != null) && (reply.getTime() <= System.currentTimeMillis())) { mentionNotification.add(reply.getPost()); notificationManager.addNotification(mentionNotification); } @@ -807,7 +858,7 @@ public class WebInterface implements CoreListener { * {@inheritDoc} */ @Override - public void markReplyKnown(Reply reply) { + public void markReplyKnown(PostReply reply) { newReplyNotification.remove(reply); localReplyNotification.remove(reply); mentionNotification.remove(reply.getPost()); @@ -828,15 +879,25 @@ public class WebInterface implements CoreListener { public void postRemoved(Post post) { newPostNotification.remove(post); localPostNotification.remove(post); + mentionNotification.remove(post); } /** * {@inheritDoc} */ @Override - public void replyRemoved(Reply reply) { + public void replyRemoved(PostReply reply) { newReplyNotification.remove(reply); localReplyNotification.remove(reply); + if (!getMentionedSones(reply.getText()).isEmpty()) { + boolean isMentioned = false; + for (PostReply existingReply : getCore().getReplies(reply.getPost())) { + isMentioned |= !reply.isKnown() && !getMentionedSones(existingReply.getText()).isEmpty(); + } + if (!isMentioned) { + mentionNotification.remove(reply.getPost()); + } + } } /** @@ -870,6 +931,44 @@ public class WebInterface implements CoreListener { * {@inheritDoc} */ @Override + public void soneInserting(Sone sone) { + TemplateNotification soneInsertNotification = getSoneInsertNotification(sone); + soneInsertNotification.set("soneStatus", "inserting"); + if (sone.getOptions().getBooleanOption("EnableSoneInsertNotifications").get()) { + notificationManager.addNotification(soneInsertNotification); + } + } + + /** + * {@inheritDoc} + */ + @Override + public void soneInserted(Sone sone, long insertDuration) { + TemplateNotification soneInsertNotification = getSoneInsertNotification(sone); + soneInsertNotification.set("soneStatus", "inserted"); + soneInsertNotification.set("insertDuration", insertDuration / 1000); + if (sone.getOptions().getBooleanOption("EnableSoneInsertNotifications").get()) { + notificationManager.addNotification(soneInsertNotification); + } + } + + /** + * {@inheritDoc} + */ + @Override + public void soneInsertAborted(Sone sone, Throwable cause) { + TemplateNotification soneInsertNotification = getSoneInsertNotification(sone); + soneInsertNotification.set("soneStatus", "insert-aborted"); + soneInsertNotification.set("insert-error", cause); + if (sone.getOptions().getBooleanOption("EnableSoneInsertNotifications").get()) { + notificationManager.addNotification(soneInsertNotification); + } + } + + /** + * {@inheritDoc} + */ + @Override public void updateFound(Version version, long releaseTime, long latestEdition) { newVersionNotification.getTemplateContext().set("latestVersion", version); newVersionNotification.getTemplateContext().set("latestEdition", latestEdition); @@ -878,6 +977,43 @@ public class WebInterface implements CoreListener { } /** + * {@inheritDoc} + */ + @Override + public void imageInsertStarted(Image image) { + insertingImagesNotification.add(image); + notificationManager.addNotification(insertingImagesNotification); + } + + /** + * {@inheritDoc} + */ + @Override + public void imageInsertAborted(Image image) { + insertingImagesNotification.remove(image); + } + + /** + * {@inheritDoc} + */ + @Override + public void imageInsertFinished(Image image) { + insertingImagesNotification.remove(image); + insertedImagesNotification.add(image); + notificationManager.addNotification(insertedImagesNotification); + } + + /** + * {@inheritDoc} + */ + @Override + public void imageInsertFailed(Image image, Throwable cause) { + insertingImagesNotification.remove(image); + imageInsertFailedNotification.add(image); + notificationManager.addNotification(imageInsertFailedNotification); + } + + /** * Template provider implementation that uses * {@link WebInterface#createReader(String)} to load templates for * inclusion. @@ -909,7 +1045,7 @@ public class WebInterface implements CoreListener { try { return templateCache.get(templateName); } catch (CacheException ce1) { - logger.log(Level.WARNING, "Could not get template for " + templateName + "!", ce1); + logger.log(Level.WARNING, String.format("Could not get template for %s!", templateName), ce1); return null; } } @@ -932,7 +1068,7 @@ public class WebInterface implements CoreListener { try { template = TemplateParser.parse(templateReader); } catch (TemplateException te1) { - logger.log(Level.WARNING, "Could not parse template “" + templateName + "” for inclusion!", te1); + logger.log(Level.WARNING, String.format("Could not parse template “%s” for inclusion!", templateName), te1); } return template; }