diff --git a/htroot/YMarks.html b/htroot/YMarks.html index cc59ee9d6..99b3759e9 100644 --- a/htroot/YMarks.html +++ b/htroot/YMarks.html @@ -3,22 +3,21 @@ YaCy Bookmarks #%env/templates/metas.template%# - - - - - - + + + + - - - - + + + + + #%env/templates/header.template%# @@ -68,16 +67,17 @@ HelpHelp --> - +
+

Tag Filter:

+

+ +

+
+

+
diff --git a/htroot/api/ymarks/add_ymark.xml b/htroot/api/ymarks/add_ymark.xml index d6880fb21..64389d7a6 100644 --- a/htroot/api/ymarks/add_ymark.xml +++ b/htroot/api/ymarks/add_ymark.xml @@ -1,2 +1,2 @@ - \ No newline at end of file + \ No newline at end of file diff --git a/htroot/api/ymarks/get_ymark.java b/htroot/api/ymarks/get_ymark.java index 35cf81653..2e05e3749 100644 --- a/htroot/api/ymarks/get_ymark.java +++ b/htroot/api/ymarks/get_ymark.java @@ -49,7 +49,7 @@ public class get_ymark { query = ".*"; qtype = YMarkEntry.BOOKMARK.TITLE.key(); page = 1; - rp = 10; + rp = 100; total = 0; sortname = YMarkEntry.BOOKMARK.TITLE.key(); sortorder = "asc"; diff --git a/htroot/api/ymarks/replace_tags.java b/htroot/api/ymarks/replace_tags.java new file mode 100644 index 000000000..06d53982d --- /dev/null +++ b/htroot/api/ymarks/replace_tags.java @@ -0,0 +1,84 @@ +import java.io.IOException; +import java.util.Iterator; +import java.util.regex.Pattern; + +import net.yacy.cora.protocol.RequestHeader; +import net.yacy.kelondro.blob.Tables.Row; +import net.yacy.kelondro.index.RowSpaceExceededException; +import net.yacy.kelondro.logging.Log; +import net.yacy.search.Switchboard; +import de.anomic.data.UserDB; +import de.anomic.data.ymark.YMarkTables; +import de.anomic.data.ymark.YMarkTables.TABLES; +import de.anomic.data.ymark.YMarkUtil; +import de.anomic.server.serverObjects; +import de.anomic.server.serverSwitch; + + +public class replace_tags { + + private static Switchboard sb = null; + private static serverObjects prop = null; + + public static serverObjects respond(final RequestHeader header, final serverObjects post, final serverSwitch env) { + sb = (Switchboard) env; + prop = new serverObjects(); + + String qtype; + String query; + String tags; + String replace; + + final UserDB.Entry user = sb.userDB.getUser(header); + final boolean isAdmin = (sb.verifyAuthentication(header, true)); + final boolean isAuthUser = user!= null && user.hasRight(UserDB.AccessRight.BOOKMARK_RIGHT); + + if(isAdmin || isAuthUser) { + final String bmk_user = (isAuthUser ? user.getUserName() : YMarkTables.USER_ADMIN); + + if(post != null) { + query = post.get("query", post.get("tags", YMarkUtil.EMPTY_STRING)); + qtype = post.get("qtype", "_tags"); + tags = post.get("tags", YMarkUtil.EMPTY_STRING); + replace = post.get("replace", YMarkUtil.EMPTY_STRING); + + } else { + query = ".*"; + qtype = YMarkUtil.EMPTY_STRING; + tags = YMarkUtil.EMPTY_STRING; + replace = YMarkUtil.EMPTY_STRING; + } + + try { + final String bmk_table = TABLES.BOOKMARKS.tablename(bmk_user); + final Iterator row_iter; + if(!query.isEmpty()) { + if(!qtype.isEmpty()) { + if(qtype.equals("_tags")) { + final String[] tagArray = YMarkUtil.cleanTagsString(query).split(YMarkUtil.TAGS_SEPARATOR); + row_iter = sb.tables.bookmarks.getBookmarksByTag(bmk_user, tagArray); + } else if(qtype.equals("_folder")) { + row_iter = sb.tables.bookmarks.getBookmarksByFolder(bmk_user, query); + } else { + row_iter = sb.tables.iterator(bmk_table, qtype, Pattern.compile(query)); + } + } else { + row_iter = sb.tables.iterator(bmk_table, Pattern.compile(query)); + } + } else { + row_iter = sb.tables.iterator(bmk_table); + } + sb.tables.bookmarks.replaceTags(row_iter, bmk_user, tags, replace); + prop.put("status", 1); + } catch (IOException e) { + Log.logException(e); + } catch (RowSpaceExceededException e) { + Log.logException(e); + } + } else { + prop.put(YMarkTables.USER_AUTHENTICATE,YMarkTables.USER_AUTHENTICATE_MSG); + } + // return rewrite properties + return prop; + } +} diff --git a/htroot/api/ymarks/replace_tags.xml b/htroot/api/ymarks/replace_tags.xml new file mode 100644 index 000000000..a72c699cc --- /dev/null +++ b/htroot/api/ymarks/replace_tags.xml @@ -0,0 +1,2 @@ + + \ No newline at end of file diff --git a/htroot/yacy/ui/css/jquery.multiselect.css b/htroot/jquery/css/jquery.multiselect.css similarity index 100% rename from htroot/yacy/ui/css/jquery.multiselect.css rename to htroot/jquery/css/jquery.multiselect.css diff --git a/htroot/jquery/js/jquery.multiselect.min.js b/htroot/jquery/js/jquery.multiselect.min.js new file mode 100644 index 000000000..aa7c62743 --- /dev/null +++ b/htroot/jquery/js/jquery.multiselect.min.js @@ -0,0 +1,20 @@ +/* + * jQuery MultiSelect UI Widget 1.11 + * Copyright (c) 2011 Eric Hynds + * + * http://www.erichynds.com/jquery/jquery-ui-multiselect-widget/ + * + * Depends: + * - jQuery 1.4.2+ + * - jQuery UI 1.8 widget factory + * + * Optional: + * - jQuery UI effects + * - jQuery UI position utility + * + * Dual licensed under the MIT and GPL licenses: + * http://www.opensource.org/licenses/mit-license.php + * http://www.gnu.org/licenses/gpl.html + * + */ +(function(d){var i=0;d.widget("ech.multiselect",{options:{header:!0,height:175,minWidth:225,classes:"",checkAllText:"Check all",uncheckAllText:"Uncheck all",noneSelectedText:"Select options",selectedText:"# selected",selectedList:0,show:"",hide:"",autoOpen:!1,multiple:!0,position:{}},_create:function(){var a=this.element.hide(),b=this.options;this.speed=d.fx.speeds._default;this._isOpen=!1;a=(this.button=d('')).addClass("ui-multiselect ui-widget ui-state-default ui-corner-all").addClass(b.classes).attr({title:a.attr("title"), "aria-haspopup":!0,tabIndex:a.attr("tabIndex")}).insertAfter(a);(this.buttonlabel=d("")).html(b.noneSelectedText).appendTo(a);var a=(this.menu=d("
")).addClass("ui-multiselect-menu ui-widget ui-widget-content ui-corner-all").addClass(b.classes).insertAfter(a),c=(this.header=d("
")).addClass("ui-widget-header ui-corner-all ui-multiselect-header ui-helper-clearfix").appendTo(a);(this.headerLinkContainer=d("
    ")).addClass("ui-helper-reset").html(function(){return b.header===!0? '
  • '+b.checkAllText+'
  • '+b.uncheckAllText+"
  • ":typeof b.header==="string"?"
  • "+b.header+"
  • ":""}).append('
  • ').appendTo(c);(this.checkboxContainer=d("
      ")).addClass("ui-multiselect-checkboxes ui-helper-reset").appendTo(a); this._bindEvents();this.refresh(!0);b.multiple||a.addClass("ui-multiselect-single")},_init:function(){this.options.header===!1&&this.header.hide();this.options.multiple||this.headerLinkContainer.find(".ui-multiselect-all, .ui-multiselect-none").hide();this.options.autoOpen&&this.open();this.element.is(":disabled")&&this.disable()},refresh:function(a){var b=this.options,c=this.menu,e=this.checkboxContainer,h=[],f=[],g=this.element.attr("id")||i++;this.element.find("option").each(function(a){d(this); var e=this.parentNode,c=this.innerHTML,i=this.title,m=this.value,a=this.id||"ui-multiselect-"+g+"-option-"+a,j=this.disabled,l=this.selected,k=["ui-corner-all"];e.tagName.toLowerCase()==="optgroup"&&(e=e.getAttribute("label"),d.inArray(e,h)===-1&&(f.push('
    • '+e+"
    • "),h.push(e)));j&&k.push("ui-state-disabled");l&&!b.multiple&&k.push("ui-state-active");f.push('
    • ');f.push('
    • ")});e.html(f.join(""));this.labels=c.find("label");this._setButtonWidth();this._setMenuWidth();this.button[0].defaultValue=this.update();a||this._trigger("refresh")},update:function(){var a= this.options,b=this.labels.find("input"),c=b.filter(":checked"),e=c.length,a=e===0?a.noneSelectedText:d.isFunction(a.selectedText)?a.selectedText.call(this,e,b.length,c.get()):/\d/.test(a.selectedList)&&a.selectedList>0&&e<=a.selectedList?c.map(function(){return this.title}).get().join(", "):a.selectedText.replace("#",e).replace("#",b.length);this.buttonlabel.html(a);return a},_bindEvents:function(){function a(){b[b._isOpen?"close":"open"]();return!1}var b=this,c=this.button;c.find("span").bind("click.multiselect", a);c.bind({click:a,keypress:function(a){switch(a.which){case 27:case 38:case 37:b.close();break;case 39:case 40:b.open()}},mouseenter:function(){c.hasClass("ui-state-disabled")||d(this).addClass("ui-state-hover")},mouseleave:function(){d(this).removeClass("ui-state-hover")},focus:function(){c.hasClass("ui-state-disabled")||d(this).addClass("ui-state-focus")},blur:function(){d(this).removeClass("ui-state-focus")}});this.header.delegate("a","click.multiselect",function(a){if(d(this).hasClass("ui-multiselect-close"))b.close(); else b[d(this).hasClass("ui-multiselect-all")?"checkAll":"uncheckAll"]();a.preventDefault()});this.menu.delegate("li.ui-multiselect-optgroup-label a","click.multiselect",function(a){a.preventDefault();var c=d(this),f=c.parent().nextUntil("li.ui-multiselect-optgroup-label").find("input:visible:not(:disabled)"),g=f.get(),c=c.parent().text();b._trigger("beforeoptgrouptoggle",a,{inputs:g,label:c})!==!1&&(b._toggleChecked(f.filter(":checked").length!==f.length,f),b._trigger("optgrouptoggle",a,{inputs:g, label:c,checked:g[0].checked}))}).delegate("label","mouseenter.multiselect",function(){d(this).hasClass("ui-state-disabled")||(b.labels.removeClass("ui-state-hover"),d(this).addClass("ui-state-hover").find("input").focus())}).delegate("label","keydown.multiselect",function(a){a.preventDefault();switch(a.which){case 9:case 27:b.close();break;case 38:case 40:case 37:case 39:b._traverse(a.which,this);break;case 13:d(this).find("input")[0].click()}}).delegate('input[type="checkbox"], input[type="radio"]', "click.multiselect",function(a){var c=d(this),f=this.value,g=this.checked,i=b.element.find("option");this.disabled||b._trigger("click",a,{value:f,text:this.title,checked:g})===!1?a.preventDefault():(c.attr("aria-selected",g),i.each(function(){if(this.value===f)(this.selected=g)?this.setAttribute("selected","selected"):this.removeAttribute("selected");else if(!b.options.multiple)this.selected=!1}),b.options.multiple||(b.labels.removeClass("ui-state-active"),c.closest("label").toggleClass("ui-state-active", g),b.close()),b.element.trigger("change"),setTimeout(d.proxy(b.update,b),10))});d(document).bind("mousedown.multiselect",function(a){b._isOpen&&!d.contains(b.menu[0],a.target)&&!d.contains(b.button[0],a.target)&&a.target!==b.button[0]&&b.close()});d(this.element[0].form).bind("reset.multiselect",function(){setTimeout(function(){b.update()},10)})},_setButtonWidth:function(){var a=this.element.outerWidth(),b=this.options;if(/\d/.test(b.minWidth)&&a-1&&e._toggleCheckbox("selected", a).call(this)});c.length&&this.element.trigger("change")},_toggleDisabled:function(a){this.button.attr({disabled:a,"aria-disabled":a})[a?"addClass":"removeClass"]("ui-state-disabled");this.menu.find("input").attr({disabled:a,"aria-disabled":a}).parent()[a?"addClass":"removeClass"]("ui-state-disabled");this.element.attr({disabled:a,"aria-disabled":a})},open:function(){var a=this.button,b=this.menu,c=this.speed,e=this.options;if(!(this._trigger("beforeopen")===!1||a.hasClass("ui-state-disabled")||this._isOpen)){var h= b.find("ul:last"),f=e.show,g=a.position();d.isArray(e.show)&&(f=e.show[0],c=e.show[1]||this.speed);h.scrollTop(0).height(e.height);d.ui.position&&!d.isEmptyObject(e.position)?(e.position.of=e.position.of||a,b.show().position(e.position).hide().show(f,c)):b.css({top:g.top+a.outerHeight(),left:g.left}).show(f,c);this.labels.eq(0).trigger("mouseover").trigger("mouseenter").find("input").trigger("focus");a.addClass("ui-state-active");this._isOpen=!0;this._trigger("open")}},close:function(){if(this._trigger("beforeclose")!== !1){var a=this.options,b=a.hide,c=this.speed;d.isArray(a.hide)&&(b=a.hide[0],c=a.hide[1]||this.speed);this.menu.hide(b,c);this.button.removeClass("ui-state-active").trigger("blur").trigger("mouseleave");this._isOpen=!1;this._trigger("close")}},enable:function(){this._toggleDisabled(!1)},disable:function(){this._toggleDisabled(!0)},checkAll:function(){this._toggleChecked(!0);this._trigger("checkAll")},uncheckAll:function(){this._toggleChecked(!1);this._trigger("uncheckAll")},getChecked:function(){return this.menu.find("input").filter(":checked")}, destroy:function(){d.Widget.prototype.destroy.call(this);this.button.remove();this.menu.remove();this.element.show();return this},isOpen:function(){return this._isOpen},widget:function(){return this.menu},_setOption:function(a,b){var c=this.menu;switch(a){case "header":c.find("div.ui-multiselect-header")[b?"show":"hide"]();break;case "checkAllText":c.find("a.ui-multiselect-all span").eq(-1).text(b);break;case "uncheckAllText":c.find("a.ui-multiselect-none span").eq(-1).text(b);break;case "height":c.find("ul:last").height(parseInt(b, 10));break;case "minWidth":this.options[a]=parseInt(b,10);this._setButtonWidth();this._setMenuWidth();break;case "selectedText":case "selectedList":case "noneSelectedText":this.options[a]=b;this.update();break;case "classes":c.add(this.button).removeClass(this.options.classes).addClass(b)}d.Widget.prototype._setOption.apply(this,arguments)}})})(jQuery); diff --git a/htroot/js/yacy-ymarks.js b/htroot/js/yacy-ymarks.js index 16cdf11cb..9e59a6970 100644 --- a/htroot/js/yacy-ymarks.js +++ b/htroot/js/yacy-ymarks.js @@ -4,6 +4,7 @@ HTMLenc = function(s) { $(document).ready(function() { var height=document.documentElement.clientHeight - 200; + qtag = ""; /* Initialize Bookmark Dialog */ bm_dialog(); @@ -113,14 +114,54 @@ $(document).ready(function() { } }); - $("#example").multiselect(); + loadTags(); }); +function loadTags() { + $("#tag_include").empty(); + $.ajax({ + type: "GET", + url: "/api/ymarks/get_tags.xml?sort=alpha", + dataType: "xml", + cache: false, + success: function(xml) { + $(xml).find('tag').each(function(){ + var count = $(this).attr('count'); + var tag = $(this).attr('tag'); + $('').appendTo('#tag_include'); + }); //close each( + $("#tag_include").multiselect({ + noneSelectedText: "Select tags ...", + height: "400", + click: function(event, ui) { + if(ui.checked) { + qtag = qtag + "," + ui.value; + } + }, + close: function() { + $('#ymarks_flexigrid').flexOptions({ + query: qtag, + qtype: "_tags", + newp: 1 + }); + $('#ymarks_flexigrid').flexReload(); + }, + beforeopen: function() { + $(this).multiselect("uncheckAll"); + }, + open: function() { + qtag = ""; + } + }); + } + }); //close $.ajax( +} + function loadTagCloud() { $("#ymarks_tagcloud *").remove(); $.ajax({ - type: "POST", + type: "GET", url: "/api/ymarks/get_tags.xml?top=25&sort=alpha", dataType: "xml", cache: false, diff --git a/htroot/yacy/ui/js/jquery.multiselect.min.js b/htroot/yacy/ui/js/jquery.multiselect.min.js deleted file mode 100644 index 9da930820..000000000 --- a/htroot/yacy/ui/js/jquery.multiselect.min.js +++ /dev/null @@ -1,20 +0,0 @@ -/* - * jQuery MultiSelect UI Widget 1.9 - * Copyright (c) 2011 Eric Hynds - * - * http://www.erichynds.com/jquery/jquery-ui-multiselect-widget/ - * - * Depends: - * - jQuery 1.4.2+ - * - jQuery UI 1.8 widget factory - * - * Optional: - * - jQuery UI effects - * - jQuery UI position utility - * - * Dual licensed under the MIT and GPL licenses: - * http://www.opensource.org/licenses/mit-license.php - * http://www.gnu.org/licenses/gpl.html - * -*/ -(function(d){var o=0;d.widget("ech.multiselect",{options:{header:true,height:175,minWidth:225,classes:"",checkAllText:"Check all",uncheckAllText:"Uncheck all",noneSelectedText:"Select options",selectedText:"# selected",selectedList:0,show:"",hide:"",autoOpen:false,multiple:true,position:{}},_create:function(){var a=this.element.hide(),b=this.options;this.speed=d.fx.speeds._default;this._isOpen=false;a=(this.button=d('')).addClass("ui-multiselect ui-widget ui-state-default ui-corner-all").addClass(b.classes).attr({title:a.attr("title"), "aria-haspopup":true}).insertAfter(a);(this.buttonlabel=d("")).html(b.noneSelectedText).appendTo(a);a=(this.menu=d("
      ")).addClass("ui-multiselect-menu ui-widget ui-widget-content ui-corner-all").addClass(b.classes).insertAfter(a);var e=(this.header=d("
      ")).addClass("ui-widget-header ui-corner-all ui-multiselect-header ui-helper-clearfix").appendTo(a);(this.headerLinkContainer=d("
        ")).addClass("ui-helper-reset").html(function(){return b.header===true?'
      • '+ b.checkAllText+'
      • '+b.uncheckAllText+"
      • ":typeof b.header==="string"?"
      • "+b.header+"
      • ":""}).append('
      • ').appendTo(e);(this.checkboxContainer=d("
          ")).addClass("ui-multiselect-checkboxes ui-helper-reset").appendTo(a);this._bindEvents(); this.refresh(true);b.multiple||a.addClass("ui-multiselect-single")},_init:function(){this.options.header===false&&this.header.hide();this.options.multiple||this.headerLinkContainer.find(".ui-multiselect-all, .ui-multiselect-none").hide();this.options.autoOpen&&this.open();this.element.is(":disabled")&&this.disable()},refresh:function(a){var b=this.options,e=this.menu,c=this.button,g=this.checkboxContainer,f=[],h=this.element.attr("id")||o++;g.empty();this.element.find("option").each(function(k){var i= d(this),m=i.html(),n=this.value;k=this.id||"ui-multiselect-"+h+"-option-"+k;var j=i.parent();i=i.is(":disabled");var l=["ui-corner-all"];if(j.is("optgroup")){j=j.attr("label");if(d.inArray(j,f)===-1){d('
        • '+j+"
        • ").addClass("ui-multiselect-optgroup-label").appendTo(g);f.push(j)}}if(n.length>0){i&&l.push("ui-state-disabled");j=d("
        • ").addClass(i?"ui-multiselect-disabled":"").appendTo(g);l=d("