Filter CSS class names, “~” is not a valid character.
authorDavid ‘Bombe’ Roden <bombe@pterodactylus.net>
Wed, 10 Nov 2010 08:59:02 +0000 (09:59 +0100)
committerDavid ‘Bombe’ Roden <bombe@pterodactylus.net>
Wed, 10 Nov 2010 08:59:02 +0000 (09:59 +0100)
src/main/java/net/pterodactylus/sone/template/CssClassNameFilter.java [new file with mode: 0644]
src/main/java/net/pterodactylus/sone/web/WebInterface.java
src/main/resources/static/javascript/sone.js
src/main/resources/templates/include/viewSone.html

diff --git a/src/main/java/net/pterodactylus/sone/template/CssClassNameFilter.java b/src/main/java/net/pterodactylus/sone/template/CssClassNameFilter.java
new file mode 100644 (file)
index 0000000..6ba5d6b
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Sone - CssClassNameFilter.java - Copyright © 2010 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
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+package net.pterodactylus.sone.template;
+
+import java.util.Map;
+
+import net.pterodactylus.util.template.DataProvider;
+import net.pterodactylus.util.template.Filter;
+
+/**
+ * Converts the {@link String} {@link String#valueOf(Object) representation} of
+ * an object to a valid CSS class name by converting all characters that are not
+ * US-ASCII letters or numbers to an underscore.
+ *
+ * @author <a href="mailto:bombe@pterodactylus.net">David ‘Bombe’ Roden</a>
+ */
+public class CssClassNameFilter implements Filter {
+
+       /**
+        * {@inheritDoc}
+        */
+       @Override
+       public Object format(DataProvider dataProvider, Object data, Map<String, String> parameters) {
+               return String.valueOf(data).replaceAll("[^a-zA-Z0-9-]", "_");
+       }
+
+}
index c0d903a..e387b44 100644 (file)
@@ -37,6 +37,7 @@ import net.pterodactylus.sone.freenet.L10nFilter;
 import net.pterodactylus.sone.freenet.wot.Identity;
 import net.pterodactylus.sone.main.SonePlugin;
 import net.pterodactylus.sone.template.CollectionAccessor;
+import net.pterodactylus.sone.template.CssClassNameFilter;
 import net.pterodactylus.sone.template.GetPagePlugin;
 import net.pterodactylus.sone.template.IdentityAccessor;
 import net.pterodactylus.sone.template.PostAccessor;
@@ -186,6 +187,7 @@ public class WebInterface {
                templateFactory.addFilter("xml", new XmlFilter());
                templateFactory.addFilter("change", new RequestChangeFilter());
                templateFactory.addFilter("match", new MatchFilter());
+               templateFactory.addFilter("css", new CssClassNameFilter());
                templateFactory.addPlugin("getpage", new GetPagePlugin());
                templateFactory.addPlugin("paginate", new PaginationPlugin());
                templateFactory.setTemplateProvider(new ClassPathTemplateProvider(templateFactory));
index 66314e1..05ab5a0 100644 (file)
@@ -112,6 +112,17 @@ function getSoneStatus(soneId) {
 }
 
 /**
+ * Filters the given Sone ID, replacing all “~” characters by an underscore.
+ *
+ * @param soneId
+ *            The Sone ID to filter
+ * @returns The filtered Sone ID
+ */
+function filterSoneId(soneId) {
+       return soneId.replace(/[^a-zA-Z0-9-]/g, "_");
+}
+
+/**
  * Updates the status of the given Sone.
  *
  * @param soneId
@@ -125,14 +136,14 @@ function getSoneStatus(soneId) {
  *            The date and time of the last update (formatted for display)
  */
 function updateSoneStatus(soneId, name, status, modified, lastUpdated) {
-       $("#sone .sone." + soneId).
+       $("#sone .sone." + filterSoneId(soneId)).
                toggleClass("unknown", status == "unknown").
                toggleClass("idle", status == "idle").
                toggleClass("inserting", status == "inserting").
                toggleClass("downloading", status == "downloading").
                toggleClass("modified", modified);
-       $("#sone .sone." + soneId + " .last-update span.time").text(lastUpdated);
-       $("#sone .sone." + soneId + " .profile-link a").text(name);
+       $("#sone .sone." + filterSoneId(soneId) + " .last-update span.time").text(lastUpdated);
+       $("#sone .sone." + filterSoneId(soneId) + " .profile-link a").text(name);
 }
 
 var watchedSones = {};
index d4e5b67..9cebc9c 100644 (file)
@@ -1,4 +1,4 @@
-<div class="sone <% sone.status|html><%if sone.modified> modified<%/if> <% sone.id|html><%if sone.local> local<%/if>">
+<div class="sone <% sone.status|html><%if sone.modified> modified<%/if> <% sone.id|css|html><%if sone.local> local<%/if>">
        <div class="id"><% sone.id|html></div>
        <div class="unknown-marker" title="<%= View.Sone.Status.Unknown|l10n|html>">?</div>
        <div class="modified-marker" title="<%= View.Sone.Status.Modified|l10n|html>">!</div>