From 2d8db7d91ec944617fe6bc8a73222f20d9649725 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Thu, 28 Oct 2021 14:25:44 -0400 Subject: [PATCH 01/14] :pencil: update readme with block description --- readme.md | 1 + readme.txt | 1 + 2 files changed, 2 insertions(+) diff --git a/readme.md b/readme.md index 958d0cf..a4026ab 100644 --- a/readme.md +++ b/readme.md @@ -16,6 +16,7 @@ BU Navigation provides key tools you need to manage large numbers of pages. * Replaces the built-in “Page Parent” and “Menu Order” dropdowns with an intuitive drag and drop interface for managing your page hierarchy * The “Edit Order” screen presents you with a holistic view of your site’s structure for bulk ordering operations * The Content Navigation widget presents a customizable sidebar navigation list fed from your natural page hierarchy +* The Navigation Block provides a navigation menu based on a customizeable parent post * Add external links to navigation lists with the “Add a Link” tool Additionally, themes that support the primary navigation feature gain the ability to display a primary navigation list fed from page order. With two lines of code any theme can benefit from this feature-rich custom menu alternative. diff --git a/readme.txt b/readme.txt index 13d9267..ce9da4e 100644 --- a/readme.txt +++ b/readme.txt @@ -16,6 +16,7 @@ BU Navigation provides key tools you need to manage large numbers of pages. * Replaces the built-in “Page Parent” and “Menu Order” dropdowns with an intuitive drag and drop interface for managing your page hierarchy * The “Edit Order” screen presents you with a holistic view of your site’s structure for bulk ordering operations * The Content Navigation widget presents a customizable sidebar navigation list fed from your natural page hierarchy +* The Navigation Block provides a navigation menu based on a customizeable parent post * Add external links to navigation lists with the “Add a Link” tool Additionally, themes that support the primary navigation feature gain the ability to display a primary navigation list fed from page order. With two lines of code any theme can benefit from this feature-rich custom menu alternative. From b04bd4fed7241d7f6307495249e946e59e714b66 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Thu, 28 Oct 2021 14:27:49 -0400 Subject: [PATCH 02/14] :bookmark: version bump to 1.3.4 --- bu-navigation.php | 4 ++-- package.json | 2 +- readme.md | 2 +- readme.txt | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/bu-navigation.php b/bu-navigation.php index b224a29..a9536f3 100644 --- a/bu-navigation.php +++ b/bu-navigation.php @@ -5,7 +5,7 @@ * Author: Boston University (IS&T) * Author URI: http://sites.bu.edu/web/ * Description: Provides alternative navigation elements designed for blogs with large page counts - * Version: 1.3.3 + * Version: 1.3.4 * Text Domain: bu-navigation * Domain Path: /languages * License: GPL2+ @@ -94,7 +94,7 @@ class BU_Navigation_Plugin { * * @var string */ - const VERSION = '1.3.3'; + const VERSION = '1.3.4'; /** * Plugin class constructor. diff --git a/package.json b/package.json index 9273586..13c66ad 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "bu-navigation", - "version": "1.3.3", + "version": "1.3.4", "description": "Provides alternative navigation elements designed for blogs with large page counts", "main": "bu-navigation.php", "directories": { diff --git a/readme.md b/readme.md index a4026ab..7a1455d 100644 --- a/readme.md +++ b/readme.md @@ -3,7 +3,7 @@ **Tags:** navigation, hierarchical, post type, boston university, bu **Requires at least:** 3.1 **Tested up to:** 5.7 -**Stable tag:** 1.3.3 +**Stable tag:** 1.3.4 **License:** GPLv2 or later **License URI:** http://www.gnu.org/licenses/gpl-2.0.html diff --git a/readme.txt b/readme.txt index ce9da4e..453d837 100644 --- a/readme.txt +++ b/readme.txt @@ -3,7 +3,7 @@ Contributors: ntk, mgburns, gcorne, jtwiest, awbauer, inderpreet99 Tags: navigation, hierarchical, post type, boston university, bu Requires at least: 3.1 Tested up to: 5.7 -Stable tag: 1.3.3 +Stable tag: 1.3.4 License: GPLv2 or later License URI: http://www.gnu.org/licenses/gpl-2.0.html From 95151358a7c5832b23efc1cdc68024621cb9e8cb Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 10:26:49 -0400 Subject: [PATCH 03/14] exclude build files from analysis in codeclimate --- .codeclimate.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.codeclimate.yml b/.codeclimate.yml index 247d121..4a0dbd3 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -7,6 +7,7 @@ exclude_patterns: - tests/ - vendor/ - node_modules/ +- build/ - "**.min.css" - "**.min.js" - "js/jquery-ui-classic.css" From 96d10a35cd202d1b0488eda67ff80be6f89bb61e Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 10:30:50 -0400 Subject: [PATCH 04/14] don't use external rulesets anymore use the rulesets in the repo instead --- .codeclimate.yml | 7 ------- 1 file changed, 7 deletions(-) diff --git a/.codeclimate.yml b/.codeclimate.yml index 4a0dbd3..3f91b44 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -13,13 +13,6 @@ exclude_patterns: - "js/jquery-ui-classic.css" - "js/jquery-ui-fresh.css" -prepare: - fetch: - - "https://raw.githubusercontent.com/bu-ist/coding-standards/master/code-climate-rule-sets/.eslintrc" - - "https://raw.githubusercontent.com/bu-ist/coding-standards/master/code-climate-rule-sets/.eslintignore" - - "https://raw.githubusercontent.com/bu-ist/coding-standards/master/code-climate-rule-sets/.mdlrc" - - "https://raw.githubusercontent.com/bu-ist/coding-standards/master/code-climate-rule-sets/markdown.rb" - plugins: csslint: enabled: false From afa82cbdaf193fc4a0f400cf792ce4f6f575563e Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 10:49:46 -0400 Subject: [PATCH 05/14] adjust readme spacing for markdownlint --- readme.md | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/readme.md b/readme.md index 7a1455d..c671b61 100644 --- a/readme.md +++ b/readme.md @@ -16,7 +16,8 @@ BU Navigation provides key tools you need to manage large numbers of pages. * Replaces the built-in “Page Parent” and “Menu Order” dropdowns with an intuitive drag and drop interface for managing your page hierarchy * The “Edit Order” screen presents you with a holistic view of your site’s structure for bulk ordering operations * The Content Navigation widget presents a customizable sidebar navigation list fed from your natural page hierarchy -* The Navigation Block provides a navigation menu based on a customizeable parent post +* The Navigation Block provides a navigation menu based on +a customizeable parent post * Add external links to navigation lists with the “Add a Link” tool Additionally, themes that support the primary navigation feature gain the ability to display a primary navigation list fed from page order. With two lines of code any theme can benefit from this feature-rich custom menu alternative. @@ -91,26 +92,32 @@ Please see this page for the details: ## Screenshots -###1. Manage your site’s page hierarchy with an easy to use drag and drop interface### +### 1. Manage your site’s page hierarchy with an easy to use drag and drop interface + ![Manage your site’s page hierarchy with an easy to use drag and drop interface](https://ps.w.org/bu-navigation/assets/screenshot-1.png) -###2. The “Add a Link” tool allows you to add external links to your navigation lists### +### 2. The “Add a Link” tool allows you to add external links to your navigation lists + ![The “Add a Link” tool allows you to add external links to your navigation lists](https://ps.w.org/bu-navigation/assets/screenshot-2.png) -###3. The “Content Navigation” widget presents a configurable sidebar navigation list### +### 3. The “Content Navigation” widget presents a configurable sidebar navigation list + ![The “Content Navigation” widget presents a configurable sidebar navigation list](https://ps.w.org/bu-navigation/assets/screenshot-3.png) -###4. The “Navigation Attributes” metabox replaces the built-in “Page Parent” and “Menu Order” dropdowns### +### 4. The “Navigation Attributes” metabox replaces the built-in “Page Parent” and “Menu Order” dropdowns + ![The “Navigation Attributes” metabox replaces the built-in “Page Parent” and “Menu Order” dropdowns](https://ps.w.org/bu-navigation/assets/screenshot-4.png) -###5. The same drag and drop view is available to move pages while editing them### +### 5. The same drag and drop view is available to move pages while editing them + ![The same drag and drop view is available to move pages while editing them](https://ps.w.org/bu-navigation/assets/screenshot-5.png) ## Changelog ### 1.3.4 -* Adds a Navigation Block that can display the same output as the widget. It can also display a navigation tree from any specified parent post. +* Adds a Navigation Block that can display the same output as the widget. +It can also display a navigation tree from any specified parent post. * Adds a wp-scripts build setup for building the block assets. ### 1.3.3 From a00d064f92456cc5a93fc31c49cadf298b17e88c Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 17:42:44 -0400 Subject: [PATCH 06/14] ignore composer included files in codeclimate --- .codeclimate.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.codeclimate.yml b/.codeclimate.yml index 3f91b44..36d219b 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -8,6 +8,7 @@ exclude_patterns: - vendor/ - node_modules/ - build/ +- composer-includes/ - "**.min.css" - "**.min.js" - "js/jquery-ui-classic.css" From 1fdc16fb216ddbc3608b636ef5583a0fd1fac771 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 17:43:14 -0400 Subject: [PATCH 07/14] spacing fixes in readme --- readme.md | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/readme.md b/readme.md index c671b61..5e8e6df 100644 --- a/readme.md +++ b/readme.md @@ -1,4 +1,5 @@ # BU Navigation + **Contributors:** ntk, mgburns, gcorne, jtwiest, awbauer, inderpreet99 **Tags:** navigation, hierarchical, post type, boston university, bu **Requires at least:** 3.1 @@ -17,7 +18,7 @@ BU Navigation provides key tools you need to manage large numbers of pages. * The “Edit Order” screen presents you with a holistic view of your site’s structure for bulk ordering operations * The Content Navigation widget presents a customizable sidebar navigation list fed from your natural page hierarchy * The Navigation Block provides a navigation menu based on -a customizeable parent post + a customizeable parent post * Add external links to navigation lists with the “Add a Link” tool Additionally, themes that support the primary navigation feature gain the ability to display a primary navigation list fed from page order. With two lines of code any theme can benefit from this feature-rich custom menu alternative. @@ -117,7 +118,7 @@ Please see this page for the details: ### 1.3.4 * Adds a Navigation Block that can display the same output as the widget. -It can also display a navigation tree from any specified parent post. + It can also display a navigation tree from any specified parent post. * Adds a wp-scripts build setup for building the block assets. ### 1.3.3 From 96be45ffe693024ce2d37f38644e409216355277 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Fri, 29 Oct 2021 17:57:48 -0400 Subject: [PATCH 08/14] disable markdown line length check because the readme.md has a lot of them, and I'd rather defer fixing them. --- .codeclimate.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.codeclimate.yml b/.codeclimate.yml index 36d219b..ba36dff 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -29,6 +29,9 @@ plugins: enabled: true markdownlint: enabled: true + checks: + MD013: + enabled: false phpcodesniffer: enabled: true config: From ac7217b7911ccc46a7e33deec478255c845dd703 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Mon, 1 Nov 2021 12:17:26 -0400 Subject: [PATCH 09/14] add version number to style enqueu for cache busting as recommended by phpcs on codeclimate --- src/block.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/block.php b/src/block.php index 9eb6ebd..d54da6f 100644 --- a/src/block.php +++ b/src/block.php @@ -153,6 +153,7 @@ function navigation_block_init() { wp_enqueue_style( 'bu-navigation-block-frontend-style', plugins_url( 'block-frontend.css', __FILE__ ), - array() + array(), + \BU_Navigation_Plugin::VERSION ); } ); From d355c547824278029ad8d2a096d6374c49f980fe Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Mon, 1 Nov 2021 14:38:50 -0400 Subject: [PATCH 10/14] set in_footer parameter to true per wp standards feedback in codeclimate --- src/block.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/block.php b/src/block.php index d54da6f..c2dac08 100644 --- a/src/block.php +++ b/src/block.php @@ -126,7 +126,8 @@ function navigation_block_init() { 'bu-navigation-block', plugins_url( '/../build/block.js', __FILE__ ), $asset_file['dependencies'], - $asset_file['version'] + $asset_file['version'], + true ); // Shared Frontend/Editor Styles. From 9814093e11d6e213e916269c5742864d0a11cd29 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Mon, 1 Nov 2021 14:45:10 -0400 Subject: [PATCH 11/14] change parameter name to be more specific, two letter parameter names are too short for the wp standards --- src/block.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/block.php b/src/block.php index c2dac08..c0dfd6e 100644 --- a/src/block.php +++ b/src/block.php @@ -23,11 +23,11 @@ function get_only_parents() { $parent_ids = array_keys( $sections['sections'] ); // Use get_nav_posts to load titles. - $parents = array_map( function( $id ) { + $parents = array_map( function( $parent_id ) { return array( - 'postid' => $id, - 'title' => html_entity_decode( \get_the_title( $id ), ENT_QUOTES, 'UTF-8' ), - 'type' => \get_post_type( $id ), + 'postid' => $parent_id, + 'title' => html_entity_decode( \get_the_title( $parent_id ), ENT_QUOTES, 'UTF-8' ), + 'type' => \get_post_type( $parent_id ), ); }, $parent_ids ); From 9c9ff6569ed4560104cf40395cdc82a6d25cfe09 Mon Sep 17 00:00:00 2001 From: Jonathan Williams Date: Mon, 1 Nov 2021 14:50:56 -0400 Subject: [PATCH 12/14] don't exclude the composer loaded code yet as the only loaded library is really intrinsic still to this plugin --- .codeclimate.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.codeclimate.yml b/.codeclimate.yml index ba36dff..e077757 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -8,7 +8,6 @@ exclude_patterns: - vendor/ - node_modules/ - build/ -- composer-includes/ - "**.min.css" - "**.min.js" - "js/jquery-ui-classic.css" From d1a764b8a14f8805f86ce667d4f5ab7820127470 Mon Sep 17 00:00:00 2001 From: Alex Caloggero Date: Thu, 26 Feb 2026 15:52:33 -0500 Subject: [PATCH 13/14] Fix/jquery deprecations (#131) * MASTER into DEVELOP (#123) * :pencil: update readme with block description * :bookmark: version bump to 1.3.4 * exclude build files from analysis in codeclimate * don't use external rulesets anymore use the rulesets in the repo instead * adjust readme spacing for markdownlint * ignore composer included files in codeclimate * spacing fixes in readme * disable markdown line length check because the readme.md has a lot of them, and I'd rather defer fixing them. * add version number to style enqueu for cache busting as recommended by phpcs on codeclimate * set in_footer parameter to true per wp standards feedback in codeclimate * change parameter name to be more specific, two letter parameter names are too short for the wp standards * don't exclude the composer loaded code yet as the only loaded library is really intrinsic still to this plugin --------- Co-authored-by: Dan Crews Co-authored-by: Jonathan Williams Co-authored-by: Jonathan Williams * Fix jquery depreciations * Replace .bind with .on and .attr with .prop * Replace .attr('checked') with .prop('checked') * Minify files * Version bump --------- Co-authored-by: Tim King <112511000+timkingbu@users.noreply.github.com> Co-authored-by: Dan Crews Co-authored-by: Jonathan Williams Co-authored-by: Jonathan Williams --- bu-navigation.php | 2 +- .../templates/widget-form.php | 2 +- js/bu-navigation.js | 10 ++++------ js/bu-navigation.min.js | 2 +- js/manage.js | 4 ++-- js/manage.min.js | 2 +- js/navigation-metabox.js | 10 +++++----- js/navigation-metabox.min.js | 2 +- package.json | 2 +- readme.md | 2 +- readme.txt | 2 +- 11 files changed, 19 insertions(+), 21 deletions(-) diff --git a/bu-navigation.php b/bu-navigation.php index a9536f3..50516ba 100644 --- a/bu-navigation.php +++ b/bu-navigation.php @@ -5,7 +5,7 @@ * Author: Boston University (IS&T) * Author URI: http://sites.bu.edu/web/ * Description: Provides alternative navigation elements designed for blogs with large page counts - * Version: 1.3.4 + * Version: 1.3.5 * Text Domain: bu-navigation * Domain Path: /languages * License: GPL2+ diff --git a/composer-includes/bu-navigation-core-widget/templates/widget-form.php b/composer-includes/bu-navigation-core-widget/templates/widget-form.php index 7a76ae1..cf83359 100644 --- a/composer-includes/bu-navigation-core-widget/templates/widget-form.php +++ b/composer-includes/bu-navigation-core-widget/templates/widget-form.php @@ -88,7 +88,7 @@ function bu_navigation_widget_number; ?>_validate(e) function bu_navigation_widget_number; ?>_title_changed() { - var is_static = jQuery('#get_field_id('navigation_title_static');?>').attr('checked'); + var is_static = jQuery('#get_field_id('navigation_title_static');?>').prop('checked'); if (is_static) { jQuery(this).siblings('input.only-if-static').attr('disabled', false); diff --git a/js/bu-navigation.js b/js/bu-navigation.js index 5346b00..7022ab4 100644 --- a/js/bu-navigation.js +++ b/js/bu-navigation.js @@ -461,7 +461,7 @@ bu.plugins.navigation = {}; // Refresh post status badges (recursively) // @todo move to callback if (c.showStatuses) { - $node.find('li').andSelf().each(function (){ + $node.find('li').addBack().each(function (){ /* CHANGE: .andSelf() -> .addBack() */ setStatusBadges($(this)); }); } @@ -1074,10 +1074,8 @@ bu.plugins.navigation = {}; }; // Prevent default right click behavior - $tree.bind('loaded.jstree', function(e,data) { - - $tree.undelegate('a', 'contextmenu.jstree'); - + $tree.on('loaded.jstree', function(e, data) { + $tree.off('contextmenu.jstree', 'a'); }); // Append options menu to each node @@ -1109,7 +1107,7 @@ bu.plugins.navigation = {}; // jstree contextmenu plugin var currentMenuTarget = null; - $tree.delegate(".edit-options", "click", function (e) { + $tree.on('click', '.edit-options', function (e) { e.preventDefault(); e.stopPropagation(); diff --git a/js/bu-navigation.min.js b/js/bu-navigation.min.js index 2216ca1..d2ebfad 100644 --- a/js/bu-navigation.min.js +++ b/js/bu-navigation.min.js @@ -1 +1 @@ -var bu=bu||{};bu.plugins=bu.plugins||{},bu.plugins.navigation={},function(t){"use strict";var o,r;bu.signals=(o={listenFor:function(e,t){var o=this._listeners;void 0===o[e]&&(o[e]=[]),o[e].push(t)},broadcast:function(e,t){var o,n=this._listeners;if(n[e])for(o=0;o ul > li").each(function(e,t){t=g(t),n=u.nodeToPost(t),t.find("> ul > li").length&&(n.children=p.getPosts(t.attr("id"))),o.push(n)}),o},p.showAll=function(){f.jstree("open_all")},p.hideAll=function(){f.jstree("close_all")},p.getPostLabel=function(e){var t=u.getNodeForPost(e);return f.jstree("get_text",t)},p.setPostLabel=function(e,t){var o=u.getNodeForPost(e);f.jstree("set_text",o,t)},p.insertPost=function(e,t){if(void 0===e)throw new TypeError("Post argument for insertPost must be defined!");var o,n,s,r,a,i,d,l;return e.post_parent=e.post_parent||0,e.menu_order=e.menu_order||1,e.post_parent?(n=u.getNodeForPost(e.post_parent),r=p.getPost(e.post_parent)):n=f,1==e.menu_order?(s=n.find("> ul > li").get(0),l="before"):0<=(a=e.menu_order-2)&&(s=n.find("> ul > li").get(a),l="after"),s||(s=n,l="inside"),i={which:s,position:l,callback:t||function(e){f.jstree("deselect_all"),f.jstree("select_node",e)}},e=bu.hooks.applyFilters("preInsertPost",e,r),d=u.postToNode(e),o=f.jstree("create_node",i.which,i.position,d,i.callback),e.ID||(e.ID=o.attr("id")),e},p.updatePost=function(e){var t,o,n=u.getNodeForPost(e);return!!n&&(t=u.nodeToPost(n),o=g.extend(!0,{},t,e),f.jstree("set_text",n,o.post_title),o.post_parent=parseInt(o.post_parent,10),o.menu_order=parseInt(o.menu_order,10),n.data("post",o),r.showStatuses&&n.find("li").andSelf().each(function(){_(g(this))}),p.broadcast("postUpdated",[o]),o)},p.removePost=function(e){var t;e&&void 0===e?(t=f.jstree("get_selected"),e=u.nodeToPost(t)):t=u.getNodeForPost(e),f.jstree("remove",t)},p.getAncestors=function(e){var t=u.getNodeForPost(e);return!1!==t&&f.jstree("get_path",t)},p.save=function(){n.rollback=f.jstree("get_rollback")},p.restore=function(){void 0!==n.rollback&&(n.rollback.d.ui.selected=g([]),g.jstree.rollback(n.rollback),n.rollback=f.jstree("get_rollback"))},p.lock=function(){f.jstree("lock")},p.unlock=function(){f.jstree("unlock")},u.nodeToPost=function(e){if(void 0===e)throw new TypeError("Invalid node!");var t=e.attr("id"),o=g.extend({},!0,e.data("post"));return-1===t.indexOf("post-new")&&(t=parseInt(u.stripNodePrefix(t),10)),o.ID=t,o.post_title=f.jstree("get_text",e),o.menu_order=e.index()+1,o.post_parent=parseInt(o.post_parent,10),o.originalParent=parseInt(o.originalParent,10),o.originalOrder=parseInt(o.originalOrder,10),o.post_meta=o.post_meta||{},bu.hooks.applyFilters("nodeToPost",o,e)},u.postToNode=function(e,t){if(void 0===e)throw new TypeError("Invalid post!");var t=t||!1,o={post_title:"(no title)",post_content:"",post_status:"new",post_type:"page",post_parent:0,menu_order:1,post_meta:{},url:""},n=g.extend({},o,e),s={attr:{id:n.ID?r.nodePrefix+n.ID:"post-new-"+u.getNextPostID(),rel:u.getRelAttrForPost(e,t)},data:{title:n.post_title},metadata:{post:n}};return bu.hooks.applyFilters("postToNode",s,n)},u.getNodeForPost=function(e){return void 0!==e&&(e&&"object"==typeof e?-1===(t=e.ID.toString()).indexOf("post-new")&&(t=r.nodePrefix+t):-1===(t=e.toString()).indexOf("post-new")&&(t=r.nodePrefix+t),!!(o=g.jstree._reference(f)._get_node("#"+t)).length&&o);var t,o},u.getNextPostID=function(){return g('[id*="post-new-"]').length},u.stripNodePrefix=function(e){return e.replace(r.nodePrefix,"")},u.getRelAttrForPost=function(e,t){var o=t?"section":e.post_type==r.linksPostType?"link":"page";return o};function d(e){var t,o,n,s;if(e=e||!1,t={excluded:{class:"excluded",label:r.statusBadgeExcluded,inherited:!1},protected:{class:"protected",label:r.statusBadgeProtected,inherited:!1}},s=o=bu.hooks.applyFilters("navStatusBadges",t),e)for(n in s={},o)o[n].hasOwnProperty("inherited")&&o[n].inherited&&(s[n]=o[n]);return s}function h(e){var t;0===e.children("ul").length?e.attr("rel","page"):e.attr("rel","section"),r.showCounts&&(t=e.parent("ul").parent("div").attr("id")!=f.attr("id")?e.parents("li:last"):e,l(t,!0))}var l=function(e,t){var o=e.find("li").length;c(e,o),t&&e.find("li").each(function(){l(g(this))})},c=function(e,t){var o,n=e.children("a");0===n.children(".title-count").children(".count").length&&n.children(".title-count").append(''),o=n.find("> .title-count > .count").empty(),t?o.text("("+t+")"):o.text("")},_=function(e){var t,o,n,s,r,a,i=e.children("a");for(r in 0===i.children(".post-statuses").length&&i.append(''),o=i.children(".post-statuses").empty(),t=u.nodeToPost(e),n=[],function(e){u.nodeToPost(e);var t,o=d({inherited:!0});for(t in o)e.parentsUntil("#"+f.attr("id"),"li").filter(function(){return g(this).data("post").post_meta[t]||g(this).data("inherited_"+t)}).length?e.data("inherited_"+t,!0):e.removeData("inherited_"+t)}(e),"publish"!=t.post_status&&n.push({class:t.post_status,label:t.post_status}),s=d())(t.post_meta[r]||e.data("inherited_"+r))&&n.push({class:s[r].class,label:s[r].label});for(a=0;a'+n[a].label+"")};f.on("loaded.jstree",function(e,t){var o=f.find("> ul > li:first-child"),n=18<=o.height()?o.height():32;f.jstree("data").data.core.li_height=n,p.broadcast("postsLoaded")}),f.on("reselect.jstree",function(e,t){p.broadcast("postsSelected")}),f.on("lazy_loaded.jstree",function(e,t){p.broadcast("lazyLoadComplete")}),f.on("load_node.jstree",function(e,t){var o;-1!==t.rslt.obj&&(o=t.rslt.obj,r.showCounts&&l(o,!0))}),f.on("clean_node.jstree",function(e,t){var o=t.rslt.obj;o&&-1!==o&&o.each(function(e,t){var o=g(t);o.data("buNavExtrasAdded")||(r.showStatuses&&_(o),o.data("buNavExtrasAdded",!0))})}),f.on("before.jstree",function(e,t){var o;switch(t.func){case"select_node":case"hover_node":case"start_drag":if((o=t.inst._get_node(t.args[0]))&&o.hasClass("denied"))return!1}}),f.on("create_node.jstree",function(e,t){var o=t.rslt.obj,n=u.nodeToPost(o);p.broadcast("postCreated",[n])}),f.on("select_node.jstree",function(e,t){var o=u.nodeToPost(t.rslt.obj);p.broadcast("postSelected",[o])}),f.on("create.jstree",function(e,t){var o=t.rslt.obj,n=t.rslt.parent,s=t.rslt.position,r=u.nodeToPost(o),a=null;-1!==n&&(a=u.nodeToPost(n),h(n)),r.post_parent=a?a.ID:0,r.menu_order=s+1,p.broadcast("postInserted",[r])}),f.on("remove.jstree",function(e,t){var o,n=t.rslt.obj,s=u.nodeToPost(n),r=t.rslt.parent;-1!==r&&h(r),p.broadcast("postRemoved",[s]),n.find("li").each(function(){(o=u.nodeToPost(g(this)))&&p.broadcast("postRemoved",[o])})}),f.on("deselect_node.jstree",function(e,t){var o=u.nodeToPost(t.rslt.obj);p.broadcast("postDeselected",[o])}),f.on("deselect_all.jstree",function(e,t){p.broadcast("postsDeselected")}),f.on("move_node.jstree",function(e,c){c.rslt.o.each(function(e,t){var o,n=g(t),s=u.nodeToPost(n),r=c.rslt.np,a=c.rslt.op,i=n.index()+1,d=0,l=0;f.attr("id")!==r.attr("id")&&(h(r),d=parseInt(u.stripNodePrefix(r.attr("id")),10)),f.attr("id")===a.attr("id")||r.is("#"+a.attr("id"))||(h(a),l=u.nodeToPost(a).ID),o=s.menu_order,s.post_parent=d,s.menu_order=i,p.updatePost(s),p.broadcast("postMoved",[s,l,o])})});return r.deselectOnDocumentClick&&g(document).on("click",function(e){var t,o;void 0!==f[0]&&(t=g.contains(f[0],e.target),o=g.contains(g("#vakata-contextmenu")[0],e.target),t||o||f.jstree("deselect_all"))}),p},navman:function(e,n){var o={};n=n||{};var i=(o=v.trees.base(e,n)).$el,t=o.data,r=o.config,s=function(e){var t=n.nodeToPost(e);o.broadcast("editPost",[t])},a=function(e){var t=n.nodeToPost(e);t.url&&window.open(t.url)},d=function(e){var t=n.nodeToPost(e);o.removePost(t)};t.treeConfig.plugins.push("contextmenu"),t.treeConfig.contextmenu={show_at_node:!1,items:function(e){var t=n.nodeToPost(e),o={edit:{label:r.optionsEditLabel,action:s},view:{label:r.optionsViewLabel,action:a},remove:{label:r.optionsTrashLabel,action:d}};return t.url||delete o.view,t.post_type===r.linksPostType&&(o.remove.label=r.optionsDeleteLabel),bu.hooks.applyFilters("navmanOptionsMenuItems",o,e)}},i.bind("loaded.jstree",function(e,t){i.undelegate("a","contextmenu.jstree")}),i.bind("clean_node.jstree",function(e,t){var o=t.rslt.obj;o&&-1!=o&&o.each(function(e,t){var o,n,s=g(t).children("a");s.children(".edit-options").length||(o=g('"),(n=s.children(".post-statuses")).length?n.before(o):s.append(o))})});var l=null;i.delegate(".edit-options","click",function(e){var t,o,n,s,r,a;e.preventDefault(),e.stopPropagation(),t=g(this).offset(),o=g(this).outerWidth(),n=g(this).outerHeight(),s=t.top,s+=n,r=t.left+o-180,a=g(this).closest("li"),i.jstree("deselect_all"),i.jstree("select_node",a),i.jstree("show_contextmenu",a,r,s),g(this).addClass("clicked"),l&&l.attr("id")!==a.attr("id")&&c(l),l=a}),g(document).on("context_hide.vakata",function(e,t){c(l)});var c=function(e){e&&e.find("> a > .edit-options").removeClass("clicked")};return i.addClass("bu-navman"),o},edit_post:function(e,o){o=o||{};var n=v.trees.base(e,o),t=n.data,s=g.extend(n.config,e||{}),r=n.$el,a=s.currentPost,i={};i.dnd={drag_container:s.treeDragContainer},g.extend(!0,t.treeConfig,i);function d(e,t){if(t.$el.is(n.$el.selector))return o.stripNodePrefix(e.attr("id"))==a.ID}bu.hooks.addFilter("canSelectNode",d),bu.hooks.addFilter("canHoverNode",d),bu.hooks.addFilter("canDragNode",d),r.bind("loaded.jstree",function(e,t){var o;s.ancestors&&s.ancestors.length?(o=s.ancestors.reverse(),l(0,o)):c()});var l=function(t,o){var e=o[t];e?!1===n.openPost(e,function(){l(t+1,o)})&&n.insertPost(e,function(e){l(t+1,o)}):c()},c=function(){o.getNodeForPost(a)?(n.selectPost(a),n.save()):n.insertPost(a,function(e){n.selectPost(a),n.save()})};return n.getCurrentPost=function(){var e=o.getNodeForPost(a);return!!e&&o.nodeToPost(e)},n.setCurrentPost=function(e){a=e},r.addClass("bu-edit-post"),n}}}(jQuery); \ No newline at end of file +var bu=bu||{};bu.plugins=bu.plugins||{},bu.plugins.navigation={},function(t){"use strict";var o,r;bu.signals=(o={listenFor:function(e,t){var o=this._listeners;void 0===o[e]&&(o[e]=[]),o[e].push(t)},broadcast:function(e,t){var o,n=this._listeners;if(n[e])for(o=0;o'),n=n.find("> .title-count > .count").empty(),o?n.text("("+o+")"):n.text(""),t&&e.find("li").each(function(){s(h(this))})}function d(e){0===e.children("ul").length?e.attr("rel","page"):e.attr("rel","section"),a.showCounts&&(e=e.parent("ul").parent("div").attr("id")!=u.attr("id")?e.parents("li:last"):e,s(e,!0))}var r,l={},a=(c=c||{},bu.signals.register(l),l.config=h.extend({},_.settings,e||{}),l.data={treeConfig:{},rollback:void 0},l.config),i=l.data,u=l.$el=h(a.el),p=(a.themePath&&document.images&&(e=new Image,r=new Image,e.src=a.themePath+"/sprite.png",r.src=a.themePath+"/throbber.gif"),i.treeConfig={plugins:["themes","types","json_data","ui","dnd","crrm","bu"],core:{animation:0,html_titles:!0},ui:{selected_parent_close:!1},themes:{theme:"bu",load_css:!1},dnd:{drag_container:document},types:{types:{default:{max_children:-1,max_depth:-1,valid_children:"all",select_node:t,hover_node:o,start_drag:n},page:{max_children:-1,max_depth:-1,valid_children:"all",select_node:t,hover_node:o,start_drag:n},section:{max_children:-1,max_depth:-1,valid_children:"all",select_node:t,hover_node:o,start_drag:n},link:{max_children:0,max_depth:0,valid_children:"none",select_node:t,hover_node:o,start_drag:n}}},json_data:{ajax:{url:a.rpcUrl,type:"POST",data:function(e){e=-1===e?{ID:0}:c.nodeToPost(e);return{child_of:e.ID,post_types:a.postTypes,post_statuses:a.postStatuses,instance:a.instance,prefix:a.nodePrefix,include_links:a.includeLinks}}},progressive_render:!0},crrm:{move:{default_position:"first",check_move:function(e){var t=c.nodeToPost(e.o),o=-1===e.cr,t=!1===t.post_meta.excluded||t.post_type===a.linksPostType,n=!0;return o&&t&&!a.allowTop&&(n=!1),bu.hooks.applyFilters("moveAllowed",n,e,l)}}},bu:{lazy_load:a.lazyLoad}},a.showCounts&&(i.treeConfig.json_data.progressive_render=!1),a.initialTreeData&&(i.treeConfig.json_data.data=a.initialTreeData),i.treeConfig=bu.hooks.applyFilters("buNavTreeSettings",i.treeConfig,u),l.initialize=function(){return u.jstree(i.treeConfig),l},l.openPost=function(e,t){e=c.getNodeForPost(e);if(t=t||h.noop,!e)return!1;u.jstree("open_node",e,t,!0)},l.selectPost=function(e,t){t=t||!0;e=c.getNodeForPost(e);t&&u.jstree("deselect_all"),u.jstree("select_node",e)},l.getSelectedPost=function(){var e=u.jstree("get_selected");return!!e.length&&c.nodeToPost(e)},l.deselectAll=function(){u.jstree("deselect_all")},l.getPost=function(e){e=c.getNodeForPost(e);return!!e&&c.nodeToPost(e)},l.getPosts=function(e){var o=[],n={},e=e?h.jstree._reference(u)._get_node("#"+e):u;return e.find("> ul > li").each(function(e,t){t=h(t),n=c.nodeToPost(t),t.find("> ul > li").length&&(n.children=l.getPosts(t.attr("id"))),o.push(n)}),o},l.showAll=function(){u.jstree("open_all")},l.hideAll=function(){u.jstree("close_all")},l.getPostLabel=function(e){e=c.getNodeForPost(e);return u.jstree("get_text",e)},l.setPostLabel=function(e,t){e=c.getNodeForPost(e);u.jstree("set_text",e,t)},l.insertPost=function(e,t){if(void 0===e)throw new TypeError("Post argument for insertPost must be defined!");var o,n,s,r,a;return e.post_parent=e.post_parent||0,e.menu_order=e.menu_order||1,e.post_parent?(r=c.getNodeForPost(e.post_parent),n=l.getPost(e.post_parent)):r=u,1==e.menu_order?(o=r.find("> ul > li").get(0),a="before"):0<=(s=e.menu_order-2)&&(o=r.find("> ul > li").get(s),a="after"),o||(o=r,a="inside"),s={which:o,position:a,callback:t||function(e){u.jstree("deselect_all"),u.jstree("select_node",e)}},e=bu.hooks.applyFilters("preInsertPost",e,n),r=c.postToNode(e),o=u.jstree("create_node",s.which,s.position,r,s.callback),e.ID||(e.ID=o.attr("id")),e},l.updatePost=function(e){var t,o=c.getNodeForPost(e);return!!o&&(t=c.nodeToPost(o),t=h.extend(!0,{},t,e),u.jstree("set_text",o,t.post_title),t.post_parent=parseInt(t.post_parent,10),t.menu_order=parseInt(t.menu_order,10),o.data("post",t),a.showStatuses&&o.find("li").addBack().each(function(){f(h(this))}),l.broadcast("postUpdated",[t]),t)},l.removePost=function(e){var t;e&&void 0===e?(t=u.jstree("get_selected"),e=c.nodeToPost(t)):t=c.getNodeForPost(e),u.jstree("remove",t)},l.getAncestors=function(e){e=c.getNodeForPost(e);return!1!==e&&u.jstree("get_path",e)},l.save=function(){i.rollback=u.jstree("get_rollback")},l.restore=function(){void 0!==i.rollback&&(i.rollback.d.ui.selected=h([]),h.jstree.rollback(i.rollback),i.rollback=u.jstree("get_rollback"))},l.lock=function(){u.jstree("lock")},l.unlock=function(){u.jstree("unlock")},c.nodeToPost=function(e){if(void 0===e)throw new TypeError("Invalid node!");var t=e.attr("id"),o=h.extend({},!0,e.data("post"));return-1===t.indexOf("post-new")&&(t=parseInt(c.stripNodePrefix(t),10)),o.ID=t,o.post_title=u.jstree("get_text",e),o.menu_order=e.index()+1,o.post_parent=parseInt(o.post_parent,10),o.originalParent=parseInt(o.originalParent,10),o.originalOrder=parseInt(o.originalOrder,10),o.post_meta=o.post_meta||{},bu.hooks.applyFilters("nodeToPost",o,e)},c.postToNode=function(e,t){if(void 0===e)throw new TypeError("Invalid post!");var t=t||!1,o=h.extend({},{post_title:"(no title)",post_content:"",post_status:"new",post_type:"page",post_parent:0,menu_order:1,post_meta:{},url:""},e),e={attr:{id:o.ID?a.nodePrefix+o.ID:"post-new-"+c.getNextPostID(),rel:c.getRelAttrForPost(e,t)},data:{title:o.post_title},metadata:{post:o}};return bu.hooks.applyFilters("postToNode",e,o)},c.getNodeForPost=function(e){var t;return void 0!==e&&(e&&"object"==typeof e?-1===(t=e.ID.toString()).indexOf("post-new")&&(t=a.nodePrefix+t):-1===(t=e.toString()).indexOf("post-new")&&(t=a.nodePrefix+t),!!(e=h.jstree._reference(u)._get_node("#"+t)).length&&e)},c.getNextPostID=function(){return h('[id*="post-new-"]').length},c.stripNodePrefix=function(e){return e.replace(a.nodePrefix,"")},c.getRelAttrForPost=function(e,t){t=t?"section":e.post_type==a.linksPostType?"link":"page";return t},function(e){var t,o,n,s;if(e=e||!1,t={excluded:{class:"excluded",label:a.statusBadgeExcluded,inherited:!1},protected:{class:"protected",label:a.statusBadgeProtected,inherited:!1}},s=o=bu.hooks.applyFilters("navStatusBadges",t),e)for(n in s={},o)o[n].hasOwnProperty("inherited")&&o[n].inherited&&(s[n]=o[n]);return s}),f=function(e){var t,o,n,s,r,a,i,d=e.children("a"),l=(0===d.children(".post-statuses").length&&d.append(''),o=d.children(".post-statuses").empty(),t=c.nodeToPost(e),n=[],e);for(i in c.nodeToPost(l),p({inherited:!0}))l.parentsUntil("#"+u.attr("id"),"li").filter(function(){return h(this).data("post").post_meta[i]||h(this).data("inherited_"+i)}).length?l.data("inherited_"+i,!0):l.removeData("inherited_"+i);for(r in"publish"!=t.post_status&&n.push({class:t.post_status,label:t.post_status}),s=p())(t.post_meta[r]||e.data("inherited_"+r))&&n.push({class:s[r].class,label:s[r].label});for(a=0;a'+n[a].label+"")};u.on("loaded.jstree",function(e,t){var o=u.find("> ul > li:first-child"),o=18<=o.height()?o.height():32;u.jstree("data").data.core.li_height=o,l.broadcast("postsLoaded")}),u.on("reselect.jstree",function(e,t){l.broadcast("postsSelected")}),u.on("lazy_loaded.jstree",function(e,t){l.broadcast("lazyLoadComplete")}),u.on("load_node.jstree",function(e,t){-1!==t.rslt.obj&&(t=t.rslt.obj,a.showCounts&&s(t,!0))}),u.on("clean_node.jstree",function(e,t){t=t.rslt.obj;t&&-1!==t&&t.each(function(e,t){t=h(t);t.data("buNavExtrasAdded")||(a.showStatuses&&f(t),t.data("buNavExtrasAdded",!0))})}),u.on("before.jstree",function(e,t){var o;switch(t.func){case"select_node":case"hover_node":case"start_drag":if((o=t.inst._get_node(t.args[0]))&&o.hasClass("denied"))return!1}}),u.on("create_node.jstree",function(e,t){t=t.rslt.obj,t=c.nodeToPost(t);l.broadcast("postCreated",[t])}),u.on("select_node.jstree",function(e,t){t=c.nodeToPost(t.rslt.obj);l.broadcast("postSelected",[t])}),u.on("create.jstree",function(e,t){var o=t.rslt.obj,n=t.rslt.parent,t=t.rslt.position,o=c.nodeToPost(o),s=null;-1!==n&&(s=c.nodeToPost(n),d(n)),o.post_parent=s?s.ID:0,o.menu_order=t+1,l.broadcast("postInserted",[o])}),u.on("remove.jstree",function(e,t){var o,n=t.rslt.obj,s=c.nodeToPost(n),t=t.rslt.parent;-1!==t&&d(t),l.broadcast("postRemoved",[s]),n.find("li").each(function(){(o=c.nodeToPost(h(this)))&&l.broadcast("postRemoved",[o])})}),u.on("deselect_node.jstree",function(e,t){t=c.nodeToPost(t.rslt.obj);l.broadcast("postDeselected",[t])}),u.on("deselect_all.jstree",function(e,t){l.broadcast("postsDeselected")}),u.on("move_node.jstree",function(e,i){i.rslt.o.each(function(e,t){var t=h(t),o=c.nodeToPost(t),n=i.rslt.np,s=i.rslt.op,t=t.index()+1,r=0,a=0;u.attr("id")!==n.attr("id")&&(d(n),r=parseInt(c.stripNodePrefix(n.attr("id")),10)),u.attr("id")===s.attr("id")||n.is("#"+s.attr("id"))||(d(s),a=c.nodeToPost(s).ID),n=o.menu_order,o.post_parent=r,o.menu_order=t,l.updatePost(o),l.broadcast("postMoved",[o,a,n])})});return a.deselectOnDocumentClick&&h(document).on("click",function(e){var t;void 0!==u[0]&&(t=h.contains(u[0],e.target),e=h.contains(h("#vakata-contextmenu")[0],e.target),t||e||u.jstree("deselect_all"))}),l},navman:function(e,n){function s(e){e=n.nodeToPost(e),t.broadcast("editPost",[e])}function r(e){(e=n.nodeToPost(e)).url&&window.open(e.url)}function a(e){e=n.nodeToPost(e),t.removePost(e)}var t={},i=(n=n||{},(t=_.trees.base(e,n)).$el),e=t.data,d=t.config,l=(e.treeConfig.plugins.push("contextmenu"),e.treeConfig.contextmenu={show_at_node:!1,items:function(e){var t=n.nodeToPost(e),o={edit:{label:d.optionsEditLabel,action:s},view:{label:d.optionsViewLabel,action:r},remove:{label:d.optionsTrashLabel,action:a}};return t.url||delete o.view,t.post_type===d.linksPostType&&(o.remove.label=d.optionsDeleteLabel),bu.hooks.applyFilters("navmanOptionsMenuItems",o,e)}},i.on("loaded.jstree",function(e,t){i.off("contextmenu.jstree","a")}),i.bind("clean_node.jstree",function(e,t){t=t.rslt.obj;t&&-1!=t&&t.each(function(e,t){var o,n,t=h(t).children("a");t.children(".edit-options").length||(o=h('"),(n=t.children(".post-statuses")).length?n.before(o):t.append(o))})}),null),c=(i.on("click",".edit-options",function(e){var t,o,n;e.preventDefault(),e.stopPropagation(),e=h(this).offset(),t=h(this).outerWidth(),n=h(this).outerHeight(),o=e.top,o+=n,n=e.left+t-180,e=h(this).closest("li"),i.jstree("deselect_all"),i.jstree("select_node",e),i.jstree("show_contextmenu",e,n,o),h(this).addClass("clicked"),l&&l.attr("id")!==e.attr("id")&&c(l),l=e}),h(document).on("context_hide.vakata",function(e,t){c(l)}),function(e){e&&e.find("> a > .edit-options").removeClass("clicked")});return i.addClass("bu-navman"),t},edit_post:function(e,o){o=o||{};function t(e,t){if(t.$el.is(n.$el.selector))return o.stripNodePrefix(e.attr("id"))==a.ID}var n=_.trees.base(e,o),s=n.data,r=h.extend(n.config,e||{}),e=n.$el,a=r.currentPost,i={},d=(i.dnd={drag_container:r.treeDragContainer},h.extend(!0,s.treeConfig,i),bu.hooks.addFilter("canSelectNode",t),bu.hooks.addFilter("canHoverNode",t),bu.hooks.addFilter("canDragNode",t),e.bind("loaded.jstree",function(e,t){var o;r.ancestors&&r.ancestors.length?(o=r.ancestors.reverse(),d(0,o)):l()}),function(t,o){var e=o[t];e?!1===n.openPost(e,function(){d(t+1,o)})&&n.insertPost(e,function(e){d(t+1,o)}):l()}),l=function(){o.getNodeForPost(a)?(n.selectPost(a),n.save()):n.insertPost(a,function(e){n.selectPost(a),n.save()})};return n.getCurrentPost=function(){var e=o.getNodeForPost(a);return!!e&&o.nodeToPost(e)},n.setCurrentPost=function(e){a=e},e.addClass("bu-edit-post"),n}}}(jQuery); \ No newline at end of file diff --git a/js/manage.js b/js/manage.js index 38c9483..901d5f8 100644 --- a/js/manage.js +++ b/js/manage.js @@ -411,8 +411,8 @@ if ((typeof bu === 'undefined') || // Clear dialog $(this.ui.urlField).attr("value", ""); $(this.ui.labelField).attr("value", ""); - $(this.ui.targetSameField).attr("checked", "checked"); - $(this.ui.targetNewField).removeAttr("checked"); + $(this.ui.targetSameField).prop("checked", true); + $(this.ui.targetNewField).prop("checked", false); this.data.currentLink = null; diff --git a/js/manage.min.js b/js/manage.min.js index 58349f9..7298955 100644 --- a/js/manage.min.js +++ b/js/manage.min.js @@ -1 +1 @@ -if("undefined"==typeof bu||void 0===bu.plugins.navigation||void 0===bu.plugins.navigation.tree)throw new TypeError("BU Navigation Manager script dependencies have not been met!");!function(l){"use strict";var n,e,d;bu.plugins.navigation.views=bu.plugins.navigation.views||{},n=bu.plugins.navigation.views.Navman={el:"#nav-tree-container",ui:{form:"#navman_form",noticesContainer:"#navman-notices",movesField:"#navman-moves",insertsField:"#navman-inserts",updatesField:"#navman-updates",deletionsField:"#navman-deletions",expandAllBtn:"#navman_expand_all",collapseAllBtn:"#navman_collapse_all",saveBtn:"#bu_navman_save"},data:{dirty:!1,deletions:[],insertions:{},updates:{},moves:{}},initialize:function(t){var i=this.settings=bu_navman_settings;i.el=this.el,d=bu.plugins.navigation.tree("navman",i),e.initialize({allowTop:!!i.allowTop,isSectionEditor:!!i.isSectionEditor}),d.listenFor("editPost",this.editPost.bind(this)),d.listenFor("postRemoved",this.postRemoved.bind(this)),d.listenFor("postMoved",this.postMoved.bind(this)),e.listenFor("linkInserted",this.linkInserted.bind(this)),e.listenFor("linkUpdated",this.linkUpdated.bind(this)),l(this.ui.form).on("submit",this.save.bind(this)),l(this.ui.expandAllBtn).on("click",this.expandAll),l(this.ui.collapseAllBtn).on("click",this.collapseAll)},expandAll:function(t){t.preventDefault(),t.stopImmediatePropagation(),d.showAll()},collapseAll:function(t){t.preventDefault(),t.stopImmediatePropagation(),d.hideAll()},editPost:function(t){var i;bu_navman_settings.linksPostType===t.post_type?e.edit(t):(i="post.php?action=edit&post="+t.ID,window.location=i)},linkInserted:function(t){this.data.insertions[t.ID]=t,this.data.dirty=!0},linkUpdated:function(t){"new"===t.post_status?this.data.insertions[t.ID]=t:this.data.updates[t.ID]=t,this.data.dirty=!0},postRemoved:function(t){var i=t.ID;i&&(void 0!==this.data.insertions[i]?delete this.data.insertions[i]:(void 0!==this.data.updates[i]?delete this.data.updates[i]:void 0!==this.data.moves[i]&&delete this.data.moves[i],this.data.deletions.push(i),this.data.dirty=!0))},postMoved:function(t){"new"!==t.post_status&&(this.data.moves[t.ID]=t,this.data.dirty=!0)},save:function(t){var e,i=this.data.deletions,n={},s={},a={};l.each(this.data.insertions,function(t,i){(e=d.getPost(t))&&(a[e.ID]=e)}),l.each(this.data.updates,function(t,i){(e=d.getPost(t))&&(s[e.ID]=e)}),l.each(this.data.moves,function(t,i){(e=d.getPost(t))&&(n[e.ID]={ID:e.ID,post_status:e.post_status,post_type:e.post_type,post_parent:e.post_parent,menu_order:e.menu_order})}),l(this.ui.deletionsField).attr("value",JSON.stringify(i)),l(this.ui.insertsField).attr("value",JSON.stringify(a)),l(this.ui.updatesField).attr("value",JSON.stringify(s)),l(this.ui.movesField).attr("value",JSON.stringify(n));var o=l(""+bu_navman_settings.saveNotice+"");l(this.ui.saveBtn).prev("img").css("visibility","visible"),this.notice(o.html(),"message"),d.lock(),this.data.dirty=!1},notice:function(t,i,e){e=e||!0;var n,s=l(this.ui.noticesContainer);e&&s.empty(),n="message"===i?"updated fade":"error",s.append('

'+t+"

")}},e=bu.plugins.navigation.views.Linkman={el:"#navman-link-editor",ui:{form:"#navman_editlink_form",addBtn:"#navman_add_link",urlField:"#editlink_address",labelField:"#editlink_label",targetNewField:"#editlink_target_new",targetSameField:"#editlink_target_same"},data:{currentLink:null,allowTop:!0,isSectionEditor:!1},initialize:function(t){t=t||{},l.extend(!0,this.data,t),bu.signals.register(this),this.$el=l(this.el),this.$form=l(this.ui.form);var i={};i[bu_navman_settings.confirmLinkBtn]=this.save.bind(this),i[bu_navman_settings.cancelLinkBtn]=this.cancel.bind(this),this.$el.dialog({autoOpen:!1,buttons:i,minWidth:400,width:500,modal:!0,resizable:!1}),l(document.body).on("click",".ui-widget-overlay, .ui-widget",this.stopPropagation),l(this.ui.addBtn).on("click",this.add.bind(this)),d.listenFor("postSelected",this.onPostSelected.bind(this)),d.listenFor("postDeselected",this.onPostDeselected.bind(this)),d.listenFor("postsDeselected",this.onPostDeselected.bind(this))},add:function(t){t.preventDefault(),t.stopPropagation();var i,e="";l(t.currentTarget).parent("li").hasClass("disabled")?(i=d.getSelectedPost(),e=bu_navman_settings.noLinksNotice,i&&bu_navman_settings.linksPostType===i.post_type?e=bu_navman_settings.noChildLinkNotice+"\n\n"+bu_navman_settings.createLinkNotice:n.settings.isSectionEditor?e=bu_navman_settings.noTopLevelNotice+"\n\n"+bu_navman_settings.createLinkNotice:n.settings.allowTop||(e=bu_navman_settings.noTopLevelNotice+"\n\n"+bu_navman_settings.createLinkNotice+"\n\n"+bu_navman_settings.allowTopNotice),alert(e)):(this.data.currentLink={post_status:"new",post_type:bu_navman_settings.linksPostType,post_meta:{}},this.$el.dialog("option","title",bu_navman_settings.addLinkDialogTitle).dialog("open"))},edit:function(t){l(this.ui.urlField).prop("value",t.post_content),l(this.ui.labelField).prop("value",t.post_title),"new"===t.post_meta.bu_link_target?l(this.ui.targetNewField).prop("checked",!0):l(this.ui.targetSameField).prop("checked",!0),this.data.currentLink=t,this.$el.dialog("option","title",bu_navman_settings.editLinkDialogTitle).dialog("open")},save:function(t){var i,e,n;t.preventDefault(),t.stopPropagation(),this.$form.valid()&&((i=this.data.currentLink).post_content=l(this.ui.urlField).prop("value"),i.post_title=l(this.ui.labelField).prop("value"),i.url=i.post_content,i.post_meta.bu_link_target=l("input[name='editlink_target']:checked").prop("value"),n=d.getSelectedPost(),i.post_parent=n?n.ID:0,i.menu_order=1,"new"!==i.post_status||i.ID?(e=d.updatePost(i),this.broadcast("linkUpdated",[e])):(e=d.insertPost(i),this.broadcast("linkInserted",[e])),this.clear(),this.$el.dialog("close"))},cancel:function(t){t.preventDefault(),t.stopPropagation(),this.$el.dialog("close"),this.clear()},clear:function(){l(this.ui.urlField).attr("value",""),l(this.ui.labelField).attr("value",""),l(this.ui.targetSameField).attr("checked","checked"),l(this.ui.targetNewField).removeAttr("checked"),this.data.currentLink=null},onPostSelected:function(t){var i=!0;t.post_type==bu_navman_settings.linksPostType&&(i=!1),(i=bu.hooks.applyFilters("navmanCanAddLink",i,t,d))?l(this.ui.addBtn).parent("li").removeClass("disabled"):l(this.ui.addBtn).parent("li").addClass("disabled")},onPostDeselected:function(){var t=this.data.allowTop;(t=bu.hooks.applyFilters("navmanCanAddLink",t))?l(this.ui.addBtn).parent("li").removeClass("disabled"):l(this.ui.addBtn).parent("li").addClass("disabled")},stopPropagation:function(t){t.stopPropagation()}},window.onbeforeunload=function(){if(n.data.dirty)return bu_navman_settings.unloadWarning}}(jQuery),jQuery(document).ready(function(t){"use strict";bu.plugins.navigation.views.Navman.initialize()}); \ No newline at end of file +if("undefined"==typeof bu||void 0===bu.plugins.navigation||void 0===bu.plugins.navigation.tree)throw new TypeError("BU Navigation Manager script dependencies have not been met!");!function(t){"use strict";var i,e,n;bu.plugins.navigation.views=bu.plugins.navigation.views||{},i=bu.plugins.navigation.views.Navman={el:"#nav-tree-container",ui:{form:"#navman_form",noticesContainer:"#navman-notices",movesField:"#navman-moves",insertsField:"#navman-inserts",updatesField:"#navman-updates",deletionsField:"#navman-deletions",expandAllBtn:"#navman_expand_all",collapseAllBtn:"#navman_collapse_all",saveBtn:"#bu_navman_save"},data:{dirty:!1,deletions:[],insertions:{},updates:{},moves:{}},initialize:function(i){var s=this.settings=bu_navman_settings;s.el=this.el,n=bu.plugins.navigation.tree("navman",s),e.initialize({allowTop:!!s.allowTop,isSectionEditor:!!s.isSectionEditor}),n.listenFor("editPost",this.editPost.bind(this)),n.listenFor("postRemoved",this.postRemoved.bind(this)),n.listenFor("postMoved",this.postMoved.bind(this)),e.listenFor("linkInserted",this.linkInserted.bind(this)),e.listenFor("linkUpdated",this.linkUpdated.bind(this)),t(this.ui.form).on("submit",this.save.bind(this)),t(this.ui.expandAllBtn).on("click",this.expandAll),t(this.ui.collapseAllBtn).on("click",this.collapseAll)},expandAll:function(t){t.preventDefault(),t.stopImmediatePropagation(),n.showAll()},collapseAll:function(t){t.preventDefault(),t.stopImmediatePropagation(),n.hideAll()},editPost:function(t){if(bu_navman_settings.linksPostType===t.post_type)e.edit(t);else{var i="post.php?action=edit&post="+t.ID;window.location=i}},linkInserted:function(t){this.data.insertions[t.ID]=t,this.data.dirty=!0},linkUpdated:function(t){"new"===t.post_status?this.data.insertions[t.ID]=t:this.data.updates[t.ID]=t,this.data.dirty=!0},postRemoved:function(t){var i=t.ID;i&&(void 0!==this.data.insertions[i]?delete this.data.insertions[i]:void 0!==this.data.updates[i]?(delete this.data.updates[i],this.data.deletions.push(i),this.data.dirty=!0):void 0!==this.data.moves[i]?(delete this.data.moves[i],this.data.deletions.push(i),this.data.dirty=!0):(this.data.deletions.push(i),this.data.dirty=!0))},postMoved:function(t){"new"!==t.post_status&&(this.data.moves[t.ID]=t,this.data.dirty=!0)},save:function(i){var e,s=this.data.deletions,a={},o={},l={};t.each(this.data.insertions,(function(t,i){(e=n.getPost(t))&&(l[e.ID]=e)})),t.each(this.data.updates,(function(t,i){(e=n.getPost(t))&&(o[e.ID]=e)})),t.each(this.data.moves,(function(t,i){(e=n.getPost(t))&&(a[e.ID]={ID:e.ID,post_status:e.post_status,post_type:e.post_type,post_parent:e.post_parent,menu_order:e.menu_order})})),t(this.ui.deletionsField).attr("value",JSON.stringify(s)),t(this.ui.insertsField).attr("value",JSON.stringify(l)),t(this.ui.updatesField).attr("value",JSON.stringify(o)),t(this.ui.movesField).attr("value",JSON.stringify(a));var d=t(""+bu_navman_settings.saveNotice+"");t(this.ui.saveBtn).prev("img").css("visibility","visible"),this.notice(d.html(),"message"),n.lock(),this.data.dirty=!1},notice:function(i,e,n){n=n||!0;var s,a=t(this.ui.noticesContainer);n&&a.empty(),s="message"===e?"updated fade":"error",a.append('

'+i+"

")}},e=bu.plugins.navigation.views.Linkman={el:"#navman-link-editor",ui:{form:"#navman_editlink_form",addBtn:"#navman_add_link",urlField:"#editlink_address",labelField:"#editlink_label",targetNewField:"#editlink_target_new",targetSameField:"#editlink_target_same"},data:{currentLink:null,allowTop:!0,isSectionEditor:!1},initialize:function(i){i=i||{},t.extend(!0,this.data,i),bu.signals.register(this),this.$el=t(this.el),this.$form=t(this.ui.form);var e={};e[bu_navman_settings.confirmLinkBtn]=this.save.bind(this),e[bu_navman_settings.cancelLinkBtn]=this.cancel.bind(this),this.$el.dialog({autoOpen:!1,buttons:e,minWidth:400,width:500,modal:!0,resizable:!1}),t(document.body).on("click",".ui-widget-overlay, .ui-widget",this.stopPropagation),t(this.ui.addBtn).on("click",this.add.bind(this)),n.listenFor("postSelected",this.onPostSelected.bind(this)),n.listenFor("postDeselected",this.onPostDeselected.bind(this)),n.listenFor("postsDeselected",this.onPostDeselected.bind(this))},add:function(e){e.preventDefault(),e.stopPropagation();var s,a="";t(e.currentTarget).parent("li").hasClass("disabled")?(s=n.getSelectedPost(),a=bu_navman_settings.noLinksNotice,s&&bu_navman_settings.linksPostType===s.post_type?a=bu_navman_settings.noChildLinkNotice+"\n\n"+bu_navman_settings.createLinkNotice:i.settings.isSectionEditor?a=bu_navman_settings.noTopLevelNotice+"\n\n"+bu_navman_settings.createLinkNotice:i.settings.allowTop||(a=bu_navman_settings.noTopLevelNotice+"\n\n"+bu_navman_settings.createLinkNotice+"\n\n"+bu_navman_settings.allowTopNotice),alert(a)):(this.data.currentLink={post_status:"new",post_type:bu_navman_settings.linksPostType,post_meta:{}},this.$el.dialog("option","title",bu_navman_settings.addLinkDialogTitle).dialog("open"))},edit:function(i){t(this.ui.urlField).prop("value",i.post_content),t(this.ui.labelField).prop("value",i.post_title),"new"===i.post_meta.bu_link_target?t(this.ui.targetNewField).prop("checked",!0):t(this.ui.targetSameField).prop("checked",!0),this.data.currentLink=i,this.$el.dialog("option","title",bu_navman_settings.editLinkDialogTitle).dialog("open")},save:function(i){if(i.preventDefault(),i.stopPropagation(),this.$form.valid()){var e,s,a=this.data.currentLink;a.post_content=t(this.ui.urlField).prop("value"),a.post_title=t(this.ui.labelField).prop("value"),a.url=a.post_content,a.post_meta.bu_link_target=t("input[name='editlink_target']:checked").prop("value"),(s=n.getSelectedPost())?(a.post_parent=s.ID,a.menu_order=1):(a.post_parent=0,a.menu_order=1),"new"!==a.post_status||a.ID?(e=n.updatePost(a),this.broadcast("linkUpdated",[e])):(e=n.insertPost(a),this.broadcast("linkInserted",[e])),this.clear(),this.$el.dialog("close")}},cancel:function(t){t.preventDefault(),t.stopPropagation(),this.$el.dialog("close"),this.clear()},clear:function(){t(this.ui.urlField).attr("value",""),t(this.ui.labelField).attr("value",""),t(this.ui.targetSameField).prop("checked",!0),t(this.ui.targetNewField).prop("checked",!1),this.data.currentLink=null},onPostSelected:function(i){var e=!0;i.post_type==bu_navman_settings.linksPostType&&(e=!1),(e=bu.hooks.applyFilters("navmanCanAddLink",e,i,n))?t(this.ui.addBtn).parent("li").removeClass("disabled"):t(this.ui.addBtn).parent("li").addClass("disabled")},onPostDeselected:function(){var i=this.data.allowTop;(i=bu.hooks.applyFilters("navmanCanAddLink",i))?t(this.ui.addBtn).parent("li").removeClass("disabled"):t(this.ui.addBtn).parent("li").addClass("disabled")},stopPropagation:function(t){t.stopPropagation()}},window.onbeforeunload=function(){if(i.data.dirty)return bu_navman_settings.unloadWarning}}(jQuery),jQuery(document).ready((function(t){"use strict";bu.plugins.navigation.views.Navman.initialize()})); \ No newline at end of file diff --git a/js/navigation-metabox.js b/js/navigation-metabox.js index 516ad8b..aed88dc 100644 --- a/js/navigation-metabox.js +++ b/js/navigation-metabox.js @@ -58,7 +58,7 @@ if((typeof bu === 'undefined' ) || currentParent = parseInt($(this.inputs['parent']).val(),10); currentOrder = parseInt($(this.inputs['order']).val(),10); navLabel = $(this.inputs['label']).val() || '(no title)'; - navDisplay = $(this.inputs['visible']).attr('checked') || false; + navDisplay = $(this.inputs['visible']).prop('checked') || false; // Create current post object this.settings.currentPost = { @@ -105,11 +105,11 @@ if((typeof bu === 'undefined' ) || attachHandlers: function() { // Modal creation on click - this.$el.delegate(this.ui.moveBtn, 'click', this.data.modalTree.open ); + this.$el.on('click', this.ui.moveBtn, this.data.modalTree.open); // Metabox actions - this.$el.delegate(this.inputs.label, 'blur', $.proxy(this.onLabelChange,this)); - this.$el.delegate(this.inputs.visible, 'click', $.proxy(this.onToggleVisibility,this)); + this.$el.on('blur', this.inputs.label, $.proxy(this.onLabelChange,this)); + this.$el.on('click', this.inputs.visible, $.proxy(this.onToggleVisibility,this)); }, @@ -128,7 +128,7 @@ if((typeof bu === 'undefined' ) || }, onToggleVisibility: function(e) { - var visible = $(e.target).attr('checked'); + var visible = $(e.target).prop('checked'); var msg = nav_metabox_settings.topLevelDisabled + "\n\n" + nav_metabox_settings.topLevelNotice; if (visible && !this.isAllowedInNavigationLists(this.settings.currentPost)) { diff --git a/js/navigation-metabox.min.js b/js/navigation-metabox.min.js index 6a192ac..419960e 100644 --- a/js/navigation-metabox.min.js +++ b/js/navigation-metabox.min.js @@ -1 +1 @@ -if("undefined"==typeof bu||void 0===bu.plugins||void 0===bu.plugins.navigation)throw new TypeError("BU Navigation Metabox dependencies have not been met!");var tb_position;!function(l){var u;bu.plugins.navigation.views=bu.plugins.navigation.views||{},bu.plugins.navigation.views.Metabox={el:"#bunavattrsdiv",ui:{treeContainer:"#edit-post-tree",moveBtn:"#move-post-button",breadcrumbs:"#bu-post-breadcrumbs"},inputs:{label:'[name="nav_label"]',visible:'[name="nav_display"]',postID:'[name="post_ID"]',originalStatus:'[name="original_post_status"]',parent:'[name="parent_id"]',order:'[name="menu_order"]',autoDraft:'[name="auto_draft"]'},data:{modalTree:void 0,breadcrumbs:"",label:""},initialize:function(){var t,e,i,n,a;return this.settings=nav_metabox_settings,this.settings.el=this.ui.treeContainer,this.settings.isNewPost=1==l(this.inputs.autoDraft).val(),t=l(this.inputs.originalStatus).val(),e=parseInt(l(this.inputs.parent).val(),10),i=parseInt(l(this.inputs.order).val(),10),n=l(this.inputs.label).val()||"(no title)",a=l(this.inputs.visible).attr("checked")||!1,this.settings.currentPost={ID:parseInt(l(this.inputs.postID).val(),10),post_title:n,post_status:"auto-draft"==t?"new":t,post_parent:e,menu_order:i,post_meta:{excluded:!a},originalParent:e,originalExclude:!a},l(this.ui.treeContainer).addClass("current-post-status-"+t),this.$el=l(this.el),this.loadNavTree(),this.attachHandlers(),this},loadNavTree:function(t){void 0===this.data.modalTree&&(this.data.modalTree=ModalPostTree(this.settings),this.data.modalTree.listenFor("locationUpdated",l.proxy(this.onLocationUpdated,this)))},attachHandlers:function(){this.$el.delegate(this.ui.moveBtn,"click",this.data.modalTree.open),this.$el.delegate(this.inputs.label,"blur",l.proxy(this.onLabelChange,this)),this.$el.delegate(this.inputs.visible,"click",l.proxy(this.onToggleVisibility,this))},onLabelChange:function(t){var e=l(this.inputs.label).attr("value");this.settings.currentPost.post_title=e,u.updatePost(this.settings.currentPost),u.save(),this.updateBreadcrumbs(this.settings.currentPost)},onToggleVisibility:function(t){var e=l(t.target).attr("checked"),i=nav_metabox_settings.topLevelDisabled+"\n\n"+nav_metabox_settings.topLevelNotice;e&&!this.isAllowedInNavigationLists(this.settings.currentPost)?(t.preventDefault(),this.notify(i)):(this.settings.currentPost.post_meta.excluded=!e,u.updatePost(this.settings.currentPost),u.save())},onLocationUpdated:function(t){l(this.inputs.parent).val(t.post_parent),l(this.inputs.order).val(t.menu_order),this.updateBreadcrumbs(t),this.settings.currentPost=t},updateBreadcrumbs:function(t){var i,n,a=u.getAncestors(t.ID);!1!==a&&(i=l(this.ui.breadcrumbs).clone().empty(),l.each(a,function(t,e){n=l("
  • ").html(e),t"):n.addClass("current"),0===t?i.append(n):i.find("ul").last().append(n)}),1'+nav_metabox_settings.topLevelLabel+""))},isAllowedInNavigationLists:function(t){return!1===t.originalExclude&&0===t.originalParent||0!==t.post_parent||this.settings.allowTop},notify:function(t){alert(t)}},ModalPostTree=bu.plugins.navigation.views.ModalPostTree=function(t){var e,r={},a=r.conf={treeContainer:"#edit-post-tree",toolbarContainer:".post-placement-toolbar",navSaveBtn:"#bu-post-placement-save",navCancelBtn:"#bu-post-placement-cancel",treeDragContainer:"#TB_ajaxContent"},a=l.extend(a,t);bu.signals.register(r);return r.open=function(t){var e=l(window).width(),i=l(window).height(),n=720").html(i),e"):s.addClass("current"),0===e?a.append(s):a.find("ul").last().append(s)})),a.find("li").length>1?t(this.ui.breadcrumbs).replaceWith(a):t(this.ui.breadcrumbs).html('
  • '+nav_metabox_settings.topLevelLabel+"
  • "))},isAllowedInNavigationLists:function(t){return!((!1!==t.originalExclude||0!==t.originalParent)&&0===t.post_parent)||this.settings.allowTop},notify:function(t){alert(t)}},ModalPostTree=bu.plugins.navigation.views.ModalPostTree=function(i){var n,a={},s=a.conf={treeContainer:"#edit-post-tree",toolbarContainer:".post-placement-toolbar",navSaveBtn:"#bu-post-placement-save",navCancelBtn:"#bu-post-placement-cancel",treeDragContainer:"#TB_ajaxContent"};s=t.extend(s,i),bu.signals.register(a);return a.open=function(i){var n=t(window).width(),s=t(window).height(),o=7200&&i.scrollTop(a))},a.onUpdateLocation=function(t){t.preventDefault(),a.broadcast("locationUpdated",[e.getCurrentPost()]),e.save(),a.saving=!0,tb_remove()},a.onCancelMove=function(t){t.preventDefault(),tb_remove()},e=a.tree=bu.plugins.navigation.tree("edit_post",s),(n=t(s.toolbarContainer)).on("click",s.navSaveBtn,a.onUpdateLocation),n.on("click",s.navCancelBtn,a.onCancelMove),s.lazyLoad?e.listenFor("lazyLoadComplete",e.save):e.listenFor("postsSelected",e.save),a}}(jQuery),function(t){tb_position=function(){var e=t("#TB_window"),i=t(window).width(),n=t(window).height(),a=720 Date: Tue, 9 Jun 2026 16:12:37 -0400 Subject: [PATCH 14/14] Make navigation tree section cache persistent The 'bu-navigation' object cache group (the load_sections section/membership structure) was registered non-persistent, so on production with an active object cache the expensive GROUP_CONCAT/GROUP BY wp_posts scan re-ran on nearly every front-end render under crawler concurrency. Leave the group persistent (Redis-backed). This is safe by construction: the cached payload is order- and status-independent parent/children membership only, keyed on core's posts 'last_changed' value (bumped by clean_post_cache() on every post insert/update/delete), so a stale entry is orphaned rather than served. Publication status, menu_order ordering, and navigation meta are applied downstream on the uncached get_nav_posts() query and are never served from this cache. Harden the cache entry with an explicit DAY_IN_SECONDS TTL backstop and a site-scoped key (get_current_blog_id()) for multisite isolation, mirroring the bu-calendar default-URL cache. Bump version to 1.3.6; also corrects the VERSION constant, which had drifted to 1.3.4 while the plugin header read 1.3.5. --- bu-navigation.php | 28 +++++++++++++------ .../src/data-model.php | 12 ++++++-- readme.md | 11 +++++++- readme.txt | 6 +++- 4 files changed, 44 insertions(+), 13 deletions(-) diff --git a/bu-navigation.php b/bu-navigation.php index 50516ba..2076bc7 100644 --- a/bu-navigation.php +++ b/bu-navigation.php @@ -5,7 +5,7 @@ * Author: Boston University (IS&T) * Author URI: http://sites.bu.edu/web/ * Description: Provides alternative navigation elements designed for blogs with large page counts - * Version: 1.3.5 + * Version: 1.3.6 * Text Domain: bu-navigation * Domain Path: /languages * License: GPL2+ @@ -94,7 +94,7 @@ class BU_Navigation_Plugin { * * @var string */ - const VERSION = '1.3.4'; + const VERSION = '1.3.6'; /** * Plugin class constructor. @@ -124,17 +124,29 @@ public function register_hooks() { } /** - * Calls wp_cache_add_non_persistent_groups() + * Object cache group configuration for the navigation tree. * - * Calling wp_cache_add_non_persistent_groups() doesn't appear to do anything - * in modern WordPress? + * The 'bu-navigation' group caches the section/membership structure built by + * load_sections() (see composer-includes/bu-navigation-core-widget/src/data-model.php). + * It is intentionally left PERSISTENT (Redis-backed in production) rather than + * registered non-persistent. + * + * This is safe by construction: the cached payload is order- and status-independent + * parent->children membership only, and its cache key is version-stamped on core's + * 'posts' last_changed value (bumped by clean_post_cache() on every post + * insert/update/delete), so a stale entry is orphaned rather than served. Publication + * status, menu_order ordering, and nav meta are all applied downstream on the uncached + * get_nav_posts() query, so they are never served from this cache. + * + * Previously this method registered the group non-persistent. On production (where an + * object cache is active) that defeated cross-request caching, forcing the expensive + * GROUP_CONCAT/GROUP BY wp_posts scan to run on nearly every front-end render under + * crawler concurrency. Leaving the group persistent removes that scan from the common + * case while preserving the existing per-request invalidation behavior. * * @return void */ public function add_cache_groups() { - if ( function_exists( 'wp_cache_add_non_persistent_groups' ) ) { - wp_cache_add_non_persistent_groups( array( 'bu-navigation' ) ); - } } /** diff --git a/composer-includes/bu-navigation-core-widget/src/data-model.php b/composer-includes/bu-navigation-core-widget/src/data-model.php index 4eedae1..a670958 100644 --- a/composer-includes/bu-navigation-core-widget/src/data-model.php +++ b/composer-includes/bu-navigation-core-widget/src/data-model.php @@ -87,7 +87,11 @@ function load_sections( $post_types = array( 'page' ), $include_links = true ) { wp_cache_set( 'last_changed', $last_changed, 'posts' ); } - $cache_key = 'all_sections:' . md5( serialize( $post_types ) . ":$last_changed" ); + // Scope the key to the current site. The 'bu-navigation' group is Redis-backed + // (persistent) in production, and although the object cache prefixes non-global + // group keys by blog, including the blog id here guarantees per-site isolation on + // multisite regardless of the drop-in's behavior. + $cache_key = 'all_sections:' . get_current_blog_id() . ':' . md5( serialize( $post_types ) . ":$last_changed" ); if ( $all_sections = wp_cache_get( $cache_key, 'bu-navigation' ) ) { return $all_sections; } @@ -105,8 +109,10 @@ function load_sections( $post_types = array( 'page' ), $include_links = true ) { $all_sections = transform_rows( $rows ); - // Cache results. - wp_cache_set( $cache_key, $all_sections, 'bu-navigation' ); + // Cache results. The version-stamped key (posts 'last_changed') is the primary + // invalidation; the explicit TTL is a self-healing backstop in case a membership + // change ever bypasses clean_post_cache() (e.g. a direct $wpdb write or import). + wp_cache_set( $cache_key, $all_sections, 'bu-navigation', DAY_IN_SECONDS ); return $all_sections; } diff --git a/readme.md b/readme.md index 4474379..f22286d 100644 --- a/readme.md +++ b/readme.md @@ -4,7 +4,7 @@ **Tags:** navigation, hierarchical, post type, boston university, bu **Requires at least:** 3.1 **Tested up to:** 5.7 -**Stable tag:** 1.3.5 +**Stable tag:** 1.3.6 **License:** GPLv2 or later **License URI:** http://www.gnu.org/licenses/gpl-2.0.html @@ -115,6 +115,15 @@ Please see this page for the details: ## Changelog +### 1.3.6 + +* Makes the navigation tree section cache (`load_sections`) persistent instead of + non-persistent, so the page-hierarchy `GROUP_CONCAT` query is reused across requests + rather than re-run on nearly every front-end render. The cache key is site-scoped and + version-stamped on the core posts cache, with a one-day TTL backstop; publication status, + ordering, and navigation meta continue to be applied on the uncached posts query, so + navigation output is unchanged. + ### 1.3.4 * Adds a Navigation Block that can display the same output as the widget. diff --git a/readme.txt b/readme.txt index dab25b5..f75743c 100644 --- a/readme.txt +++ b/readme.txt @@ -3,7 +3,7 @@ Contributors: ntk, mgburns, gcorne, jtwiest, awbauer, inderpreet99 Tags: navigation, hierarchical, post type, boston university, bu Requires at least: 3.1 Tested up to: 5.7 -Stable tag: 1.3.5 +Stable tag: 1.3.6 License: GPLv2 or later License URI: http://www.gnu.org/licenses/gpl-2.0.html @@ -79,6 +79,10 @@ Please see this page for the details: == Changelog == += 1.3.6 = + +* Makes the navigation tree section cache (`load_sections`) persistent instead of non-persistent, so the page-hierarchy `GROUP_CONCAT` query is reused across requests rather than re-run on nearly every front-end render. The cache key is site-scoped and version-stamped on the core posts cache, with a one-day TTL backstop; publication status, ordering, and navigation meta continue to be applied on the uncached posts query, so navigation output is unchanged. + = 1.3.4 = * Adds a Navigation Block that can display the same output as the widget. It can also display a navigation tree from any specified parent post.