您好!欢迎来到黑域吧资源网!本站资源24小时自动发货,请放心选购,一次付费,终身下载,售后请联系客服!

WordPress多种分类法混合查询优化方案

作者 : 黑域吧 本文共2963个字,预计阅读时间需要8分钟 发布时间: 2020-09-19 共63人阅读

我们在使用wordpress建站,特别是一些CMS类型的站点,多种分类法是常用的,然而WordPress在使用多种分类法混合查询的时候,这个查询语句就复杂了,在分类和文章数量多了之后,速度就堪忧了,所以这里提一种优化方案供参考。

举例:某个案例中,对于默认的除了的categorypost_tag,新增了一个名为kind的分类法,注册新分类法的步骤这里就不赘述了,然后我们需要查询出同时归属于categoryID为1,kind的ID为2的文章,普通的做法:

$args = array( 
  'post_type'=>'post',
  'tax_query'=>array(
    'relation'=>'AND',
    array(
      'taxonomy'=>'category',
      'field'=>'term_id',
      'operator'=>'IN',
      'terms'=>array(1)
    ),
    array(
      'taxonomy'=>'kind',
      'field'=>'term_id',
      'operator'=>'IN',
      'terms'=>array(2),
    )
  )
);
query_posts($args);

就上面这个查询来说,在没有缓存的情况下要执行3次数据库查询,前面两次分别查询对应的分类是否存在,重点是第3次文章查询,由于wordpress分类和文章的对应关系存储wp_term_relationships表中,每篇文章对应每一个分类都有一条记录,所以查询文章的时候主要要两次left join这个wp_term_relationships表,一旦数据量多起来,这样的查询就比较慢了,附打印出的查询语句如下。

 

SELECT SQL_CALC_FOUND_ROWS  wp_posts.ID FROM wp_posts  LEFT JOIN wp_term_relationships ON (wp_posts.ID = wp_term_relationships.object_id)  LEFT JOIN wp_term_relationships AS tt1 ON (wp_posts.ID = tt1.object_id) WHERE 1=1  AND ( 
  wp_term_relationships.term_taxonomy_id IN (1) 
  AND 
  tt1.term_taxonomy_id IN (2)
) AND wp_posts.post_type = 'post' AND (wp_posts.post_status = 'publish' OR wp_posts.post_status = 'private') GROUP BY wp_posts.ID ORDER BY wp_posts.post_date DESC LIMIT 0, 10

我的解决方案,在wp_posts表中增加一个字段,用来存储器中的一个分类的信息,比如这个案例里面我把kind的ID信息冗余存储在wp_posts表中,然后将查询条件放到wp_posts表中,这样就能提速了。

第一步:在启用主题的时候,执行sql在wp_posts表中增加kind_id字段,并加上Index索引。(在这个案例中因为客户的分类可以确定是单选,所以kind_id字段的类型就直接用int了,如果你要保存多个分类ID,可以改为varchar类型,不过varchar类型就不别弄索引了)。

//激活主题时执行
function ashu_add_pages() {
  global $pagenow;
  if ( 'themes.php' == $pagenow && isset( $_GET['activated'] ) ){
    ashuwp_alter_posts_table();
  }
}
add_action( 'load-themes.php', 'ashu_add_pages' );
 
//修改posts表,增加一列kind_id
function ashuwp_alter_posts_table(){
  global $wpdb;
 
  //判断字段是否已经存在
  $sql1 = "Describe {$wpdb->posts} `kind_id`";
  $kind_id_exist = $wpdb->query($sql1);
 
  if( !$kind_id_exist ){
    //新增列
    $add_column = "ALTER TABLE {$wpdb->posts} ADD COLUMN `kind_id` INT(10) DEFAULT NULL";
    $wpdb->query($add_column);
 
    //添加索引
    $add_index = "ALTER TABLE {$wpdb->posts} ADD INDEX kind_id (`kind_id`)";
    $wpdb->query($add_index);
 
  }
 
}

第二步:发布文章的时候,将kind分类的ID信息保存到wp_posts表中的kind_id字段。这里使用set_object_terms钩子,就是在设置分类的时候用,当然为了避免后台多选,这里只保存一个ID数据

 

add_action( 'set_object_terms', 'ashuwp_add_post_kind_id', 10, 6);
function ashuwp_add_post_kind_id( $object_id, $terms, $tt_ids, $taxonomy, $append = false, $old_tt_ids = array() ){
 
  global $wpdb;
  if( $taxonomy=='kind' ){
    $term_id = reset( $tt_ids );
    if( $term_id ){
      $sql = "UPDATE {$wpdb->posts} SET `kind_id`={$term_id}  where `ID`={$object_id}";
      $wpdb->get_results( $sql );
    }
  }
 
}

第三步:我希望在使用WP_Query查询文章时直接传入kind_id参数即可,所以使用posts_where钩子,检测是否有kind_id参数,然后拼接查询语句。

function ashuwp_query_posts_where( $where, $query){
  global $wpdb;
 
  $qv = $query->query_vars;
 
  isset( $qv['kind_id'] ) AND $kind_id = absint($qv['kind_id']) AND $where .= " AND {$wpdb->posts}.kind_id = {$kind_id}";
 
  return $where;
 
}
add_filter( 'posts_where', 'ashuwp_query_posts_where', 10, 2);

第四步:查询文章。最开始那一段查询可以直接改成如下代码即可。

$args = array( 
  'post_type'=>'post',
  'kind_id'=>2, //直接使用kind_id做参数
  'tax_query'=>array(
    array(
      'taxonomy'=>'category',
      'field'=>'term_id',
      'operator'=>'IN',
      'terms'=>array(1)
    )
  )
);
query_posts($args);

好了,就到这里,这里在下只是提供了一种WordPress的查询优化方案,可用此方案自行改造其他应用。

提示:
1. 本站所有资源来源于用户上传和网络,如有侵权请邮件联系站长!邮箱:(332547532@qq.com)
2. 分享目的仅供大家学习和交流,请不要用于商业用途!QQ群: 10563080
3. 如果你也有好源码或者教程,可以到审核区发布,分享有金币奖励和额外收入!
4. 本站提供的源码、模板、插件等等其他资源,都不包含技术服务 请大家谅解!
5. 如有链接无法下载、失效或广告,请点击右下方联系站长,可领回失去的金币,并额外有奖!
6. 如遇到加密压缩包,默认解压密码请在"下载框架提示方寻找",如遇到无法解压的请联系管理员!
黑域吧资源网 » WordPress多种分类法混合查询优化方案

发表评论

售后服务:

  • 售后服务范围 1、商业模板使用范围内问题免费咨询
    2、源码安装、模板安装(一般 ¥50-300)服务答疑仅限SVIP用户
    3、单价超过200元的模板免费一次安装,需提供服务器信息。
    付费增值服务 1、提供dedecms模板、WordPress主题、discuz模板优化等服务请详询在线客服
    2、承接 WordPress、DedeCMS、Discuz 等系统建站、仿站、开发、定制等服务
    3、服务器环境配置(一般 ¥50-300)
    4、网站中毒处理(需额外付费,500元/次/质保三个月)
    售后服务时间 周一至周日(法定节假日除外) 9:00-23:00
    免责声明 本站所提供的源码等资源仅供学习交流,若使用商业用途,请购买正版授权,否则产生的一切后果将由下载用户自行承担,有部分资源为网上收集或仿制而来,若模板侵犯了您的合法权益,请来信通知我们(Email: 332547532@qq.com),我们会及时删除,给您带来的不便,我们深表歉意!

Hi, 如果你对这款模板有疑问,可以跟我联系哦!

联系作者
开通SVIP 享更多特权,建议使用 QQ 登录
喜欢我嘛?喜欢就按“ctrl+D”收藏我吧!♡