@@ -972,10 +972,35 @@ function redirect_guess_404_permalink() {
972972 */
973973 $ strict_guess = apply_filters ( 'strict_redirect_guess_404_permalink ' , false );
974974
975+ // Build WP_Query arguments.
976+ $ query_args = array (
977+ 'post_status ' => $ publicly_viewable_statuses ,
978+ 'posts_per_page ' => 1 ,
979+ 'no_found_rows ' => true ,
980+ 'ignore_sticky_posts ' => true ,
981+ 'fields ' => 'ids ' ,
982+ );
983+
984+ // Handle strict vs. loose post_name matching.
975985 if ( $ strict_guess ) {
976- $ where = $ wpdb -> prepare ( ' post_name = %s ' , get_query_var ( 'name ' ) );
986+ $ query_args [ ' name ' ] = get_query_var ( 'name ' );
977987 } else {
978- $ where = $ wpdb ->prepare ( 'post_name LIKE %s ' , $ wpdb ->esc_like ( get_query_var ( 'name ' ) ) . '% ' );
988+ // For loose matching (LIKE), we'll use a posts_where filter.
989+ $ post_name_for_filter = get_query_var ( 'name ' );
990+
991+ // Store the filter callback so we can remove it later.
992+ $ post_name_where_filter = function ( $ where , $ query ) use ( $ post_name_for_filter , $ wpdb ) {
993+ // Only apply to our specific query.
994+ if ( isset ( $ query ->query_vars ['redirect_guess_404 ' ] ) && $ query ->query_vars ['redirect_guess_404 ' ] ) {
995+ $ where .= $ wpdb ->prepare ( " AND {$ wpdb ->posts }.post_name LIKE %s " , $ wpdb ->esc_like ( $ post_name_for_filter ) . '% ' );
996+ }
997+ return $ where ;
998+ };
999+
1000+ add_filter ( 'posts_where ' , $ post_name_where_filter , 10 , 2 );
1001+
1002+ // Mark this query so our filter knows to apply the LIKE clause.
1003+ $ query_args ['redirect_guess_404 ' ] = true ;
9791004 }
9801005
9811006 // If any of post_type, year, monthnum, or day are set, use them to refine the query.
@@ -985,34 +1010,46 @@ function redirect_guess_404_permalink() {
9851010 if ( empty ( $ post_types ) ) {
9861011 return false ;
9871012 }
988- $ where .= " AND post_type IN (' " . join ( " ', ' " , esc_sql ( get_query_var ( ' post_type ' ) ) ) . " ') " ;
1013+ $ query_args [ ' post_type '] = $ post_types ;
9891014 } else {
9901015 if ( ! in_array ( get_query_var ( 'post_type ' ), $ publicly_viewable_post_types , true ) ) {
9911016 return false ;
9921017 }
993- $ where .= $ wpdb -> prepare ( ' AND post_type = %s ' , get_query_var ( 'post_type ' ) );
1018+ $ query_args [ ' post_type ' ] = get_query_var ( 'post_type ' );
9941019 }
9951020 } else {
996- $ where .= " AND post_type IN (' " . implode ( " ', ' " , esc_sql ( $ publicly_viewable_post_types ) ) . " ') " ;
1021+ $ query_args [ ' post_type ' ] = $ publicly_viewable_post_types ;
9971022 }
9981023
1024+ // Handle date queries.
1025+ $ date_query = array ();
9991026 if ( get_query_var ( 'year ' ) ) {
1000- $ where .= $ wpdb -> prepare ( ' AND YEAR(post_date) = %d ' , get_query_var ( 'year ' ) );
1027+ $ date_query [ ' year ' ] = get_query_var ( 'year ' );
10011028 }
10021029 if ( get_query_var ( 'monthnum ' ) ) {
1003- $ where .= $ wpdb -> prepare ( ' AND MONTH(post_date) = %d ' , get_query_var ( 'monthnum ' ) );
1030+ $ date_query [ ' month ' ] = get_query_var ( 'monthnum ' );
10041031 }
10051032 if ( get_query_var ( 'day ' ) ) {
1006- $ where .= $ wpdb -> prepare ( ' AND DAYOFMONTH(post_date) = %d ' , get_query_var ( 'day ' ) );
1033+ $ date_query [ ' day ' ] = get_query_var ( 'day ' );
10071034 }
1035+ if ( ! empty ( $ date_query ) ) {
1036+ $ query_args ['date_query ' ] = array ( $ date_query );
1037+ }
1038+
1039+ // Execute the query.
1040+ $ query = new WP_Query ( $ query_args );
10081041
1009- // phpcs:ignore WordPress.DB.PreparedSQL.InterpolatedNotPrepared
1010- $ post_id = $ wpdb ->get_var ( "SELECT ID FROM $ wpdb ->posts WHERE $ where AND post_status IN (' " . implode ( "', ' " , esc_sql ( $ publicly_viewable_statuses ) ) . "') " );
1042+ // Clean up the filter if we added it (remove only our specific callback).
1043+ if ( ! $ strict_guess && isset ( $ post_name_where_filter ) ) {
1044+ remove_filter ( 'posts_where ' , $ post_name_where_filter , 10 );
1045+ }
10111046
1012- if ( ! $ post_id ) {
1047+ if ( empty ( $ query -> posts ) ) {
10131048 return false ;
10141049 }
10151050
1051+ $ post_id = $ query ->posts [0 ];
1052+
10161053 if ( get_query_var ( 'feed ' ) ) {
10171054 return get_post_comments_feed_link ( $ post_id , get_query_var ( 'feed ' ) );
10181055 } elseif ( get_query_var ( 'page ' ) > 1 ) {
0 commit comments