@@ -643,54 +643,54 @@ private function add_or_update_item( $method, $type, $args, $assoc_args ) {
643643 // Fetch all menu items sorted by their raw menu_order to determine
644644 // normalized (1-indexed) ranks, since wp_get_nav_menu_items(ARRAY_A)
645645 // normalises menu_order to 1,2,3… which may differ from the raw DB values.
646- $ sorted_item_ids = get_posts (
647- [
648- 'post_type ' => 'nav_menu_item ' ,
649- 'numberposts ' => -1 ,
650- 'orderby ' => 'menu_order ' ,
651- 'order ' => 'ASC ' ,
652- 'post_status ' => 'any ' ,
653- 'tax_query ' => [
654- [
655- 'taxonomy ' => 'nav_menu ' ,
656- 'field ' => 'term_taxonomy_id ' ,
657- 'terms ' => $ menu ->term_taxonomy_id ,
658- ],
659- ],
660- 'fields ' => 'ids ' ,
661- ]
662- );
663-
664- // Clamp the requested position to the valid range of menu items.
665- $ max_position = count ( $ sorted_item_ids );
666- if ( $ max_position > 0 && $ new_position > $ max_position ) {
667- // Treat out-of-range positions as "move to end", consistent with core behavior.
668- $ new_position = $ max_position ;
669- }
670-
671- // Find the 1-indexed normalized rank of the item being moved.
672- $ item_idx = array_search ( (string ) $ menu_item_db_id , $ sorted_item_ids , true );
673- $ old_position_normalized = ( false !== $ item_idx ) ? $ item_idx + 1 : 0 ;
674-
675- if ( $ old_position_normalized > 0 && $ new_position !== $ old_position_normalized ) {
676- if ( $ new_position < $ old_position_normalized ) {
677- // Moving up: items at 0-indexed [new_pos-1, old_pos-2] shift down by +1.
678- for ( $ i = $ new_position - 1 ; $ i <= $ old_position_normalized - 2 ; $ i ++ ) {
679- $ pending_menu_order_updates [] = [
680- 'ID ' => $ sorted_item_ids [ $ i ],
681- 'menu_order ' => $ i + 2 ,
682- ];
683- }
684- } else {
685- // Moving down: items at 0-indexed [old_pos, new_pos-1] shift up by -1.
686- for ( $ i = $ old_position_normalized ; $ i <= $ new_position - 1 ; $ i ++ ) {
687- $ pending_menu_order_updates [] = [
688- 'ID ' => $ sorted_item_ids [ $ i ],
689- 'menu_order ' => $ i ,
690- ];
691- }
692- }
693- }
646+ $ sorted_item_ids = get_posts (
647+ [
648+ 'post_type ' => 'nav_menu_item ' ,
649+ 'numberposts ' => -1 ,
650+ 'orderby ' => 'menu_order ' ,
651+ 'order ' => 'ASC ' ,
652+ 'post_status ' => 'any ' ,
653+ 'tax_query ' => [
654+ [
655+ 'taxonomy ' => 'nav_menu ' ,
656+ 'field ' => 'term_taxonomy_id ' ,
657+ 'terms ' => $ menu ->term_taxonomy_id ,
658+ ],
659+ ],
660+ 'fields ' => 'ids ' ,
661+ ]
662+ );
663+
664+ // Clamp the requested position to the valid range of menu items.
665+ $ max_position = count ( $ sorted_item_ids );
666+ if ( $ max_position > 0 && $ new_position > $ max_position ) {
667+ // Treat out-of-range positions as "move to end", consistent with core behavior.
668+ $ new_position = $ max_position ;
669+ }
670+
671+ // Find the 1-indexed normalized rank of the item being moved.
672+ $ item_idx = array_search ( (string ) $ menu_item_db_id , $ sorted_item_ids , true );
673+ $ old_position_normalized = ( false !== $ item_idx ) ? $ item_idx + 1 : 0 ;
674+
675+ if ( $ old_position_normalized > 0 && $ new_position !== $ old_position_normalized ) {
676+ if ( $ new_position < $ old_position_normalized ) {
677+ // Moving up: items at 0-indexed [new_pos-1, old_pos-2] shift down by +1.
678+ for ( $ i = $ new_position - 1 ; $ i <= $ old_position_normalized - 2 ; $ i ++ ) {
679+ $ pending_menu_order_updates [] = [
680+ 'ID ' => $ sorted_item_ids [ $ i ],
681+ 'menu_order ' => $ i + 2 ,
682+ ];
683+ }
684+ } else {
685+ // Moving down: items at 0-indexed [old_pos, new_pos-1] shift up by -1.
686+ for ( $ i = $ old_position_normalized ; $ i <= $ new_position - 1 ; $ i ++ ) {
687+ $ pending_menu_order_updates [] = [
688+ 'ID ' => $ sorted_item_ids [ $ i ],
689+ 'menu_order ' => $ i ,
690+ ];
691+ }
692+ }
693+ }
694694 }
695695 }
696696
@@ -706,25 +706,25 @@ private function add_or_update_item( $method, $type, $args, $assoc_args ) {
706706 }
707707 } else {
708708 // Apply deferred reordering of other menu items only after a successful update.
709- if ( ! empty ( $ pending_menu_order_updates ) ) {
710- global $ wpdb ;
711-
712- $ ids_to_update = [];
713- $ case_clauses = '' ;
714- foreach ( $ pending_menu_order_updates as $ update_args ) {
715- $ item_id = (int ) $ update_args ['ID ' ];
716- $ ids_to_update [] = $ item_id ;
717- $ case_clauses .= $ wpdb ->prepare ( ' WHEN %d THEN %d ' , $ item_id , $ update_args ['menu_order ' ] );
718- }
719-
720- $ ids_sql = implode ( ', ' , $ ids_to_update );
721- // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared -- $case_clauses and $ids_sql are constructed from prepared/safe values.
722- $ wpdb ->query ( "UPDATE {$ wpdb ->posts } SET menu_order = CASE ID {$ case_clauses } END WHERE ID IN ( {$ ids_sql }) " );
723-
724- foreach ( $ ids_to_update as $ id ) {
725- clean_post_cache ( $ id );
726- }
727- }
709+ if ( ! empty ( $ pending_menu_order_updates ) ) {
710+ global $ wpdb ;
711+
712+ $ ids_to_update = [];
713+ $ case_clauses = '' ;
714+ foreach ( $ pending_menu_order_updates as $ update_args ) {
715+ $ item_id = (int ) $ update_args ['ID ' ];
716+ $ ids_to_update [] = $ item_id ;
717+ $ case_clauses .= $ wpdb ->prepare ( ' WHEN %d THEN %d ' , $ item_id , $ update_args ['menu_order ' ] );
718+ }
719+
720+ $ ids_sql = implode ( ', ' , $ ids_to_update );
721+ // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared -- $case_clauses and $ids_sql are constructed from prepared/safe values.
722+ $ wpdb ->query ( "UPDATE {$ wpdb ->posts } SET menu_order = CASE ID {$ case_clauses } END WHERE ID IN ( {$ ids_sql }) " );
723+
724+ foreach ( $ ids_to_update as $ id ) {
725+ clean_post_cache ( $ id );
726+ }
727+ }
728728
729729 if ( ( 'add ' === $ method ) && $ menu_item_args ['menu-item-position ' ] ) {
730730 $ this ->reorder_menu_items ( $ menu ->term_id , $ menu_item_args ['menu-item-position ' ], +1 , $ result );
0 commit comments