Sora33 2023-04-30 23:36 采纳率: 0%
浏览 18

【shardingJDBC】不能根据分片列进行查询

版本:SpringBoot3.0.5 ShardingJDBC为5.2.1

假设我按照id进行分片存储,是没有问题的,但是查询的时候按照id匹配则报以下的错误,用除id以外的字段没问题

img

同理,我把分片字段改为age后,可以按照id查询,但是age也报这个错。这是什么情况

  • 写回答

1条回答 默认 最新

  • CSDN-Ada助手 CSDN-AI 官方账号 2023-05-04 16:40
    关注
    不知道你这个问题是否已经解决, 如果还没有解决的话:
    • 你看下这篇博客吧, 应该有用👉 :SpringBoot集成ShardingJDBC系列【1】—— 添加依赖
    • 除此之外, 这篇博客: springboot2.x集成shardingjdbc5.1.1实现分表/分库查询中的 实现一个自定义分片算法 部分也许能够解决你的问题, 你可以仔细阅读以下内容或者直接跳转源博客中阅读:

      经过一段源码研究,可能是设计者为了插件化考虑,在上面SPI提供的内置分片算法规则中,提供了一个ClassBasedShardingAlgorithm这个算法,其内部根据设置property,将自定义的算法通过反射创建出来。
      在这里插入图片描述

      下面是ClassBasedShardingAlgorithm算法部分源码

      public final class ClassBasedShardingAlgorithm implements StandardShardingAlgorithm<Comparable<?>>, ComplexKeysShardingAlgorithm<Comparable<?>>, HintShardingAlgorithm<Comparable<?>> {
      
          private static final String STRATEGY_KEY = "strategy";
      
          private static final String ALGORITHM_CLASS_NAME_KEY = "algorithmClassName";
          ...
          
          @Getter
          @Setter
          private Properties props = new Properties();
      
          @Override
          public void init() {
              String strategyKey = props.getProperty(STRATEGY_KEY);
              Preconditions.checkNotNull(strategyKey, "The props `%s` cannot be null when uses class based sharding strategy.", STRATEGY_KEY);
              strategy = ClassBasedShardingAlgorithmStrategyType.valueOf(strategyKey.toUpperCase().trim());
              algorithmClassName = props.getProperty(ALGORITHM_CLASS_NAME_KEY);#读取配置中的props ,取得自定义算法类
              Preconditions.checkNotNull(algorithmClassName, "The props `%s` cannot be null when uses class based sharding strategy.", ALGORITHM_CLASS_NAME_KEY);
              createAlgorithmInstance();
          }
      
          private void createAlgorithmInstance() {
              switch (strategy) {
                  case STANDARD:
                      standardShardingAlgorithm = ClassBasedShardingAlgorithmFactory.newInstance(algorithmClassName, StandardShardingAlgorithm.class, props);#就在这里反射创建实例
                      break;
                  case COMPLEX:
                      complexKeysShardingAlgorithm = ClassBasedShardingAlgorithmFactory.newInstance(algorithmClassName, ComplexKeysShardingAlgorithm.class, props);
                      break;
                  case HINT:
                      hintShardingAlgorithm = ClassBasedShardingAlgorithmFactory.newInstance(algorithmClassName, HintShardingAlgorithm.class, props);
                      break;
                  default:
                      break;
              }
          }
      
          @Override
          public String doSharding(final Collection<String> availableTargetNames, final PreciseShardingValue<Comparable<?>> shardingValue) {
              return standardShardingAlgorithm.doSharding(availableTargetNames, shardingValue); #实际上用反射出来的实例去计算
          }
      
      

      因此改一下配置

        shardingsphere:
          mode:
            type: Memory
          datasource:
            names: master
            master:
              url: jdbc:mysql://192.168.1.55:3306/demoDb?useUnicode=true&characterEncoding=UTF-8&autoReconnect=true&useAffectedRows=true&serverTimezone=GMT%2B8&useSSL=false&allowPublicKeyRetrieval=true
              driver-class-name: com.mysql.cj.jdbc.Driver
              username: demo
              password: 12345678
              type: com.alibaba.druid.pool.DruidDataSource
          rules:
            sharding:
              binding-tables:
                - "sys_user"
              tables:
                sys_user:
                  actual-data-nodes: master.sys_user_$->{0..1}
                  table-strategy:
                    standard:
                      sharding-column: id
                      sharding-algorithm-name: myShardingAlgorithm  #引用算法名称
              sharding-algorithms:
                idModShardingAlgorithm:
                  props:
                    sharding-count: 2
                  type: MOD
                myShardingAlgorithm:   #新加的算法名称
                  props:
                    strategy: standard
                    # 自定义标准分配算法
                    algorithmClassName: com.kuizii.demo.core.config.IdModShardingAlgorithm
                  type: CLASS_BASED
      

      自定义一个算法

      public class IdModShardingAlgorithm implements StandardShardingAlgorithm<String> {
          @Override
          public String doSharding(Collection<String> collection, PreciseShardingValue<String> preciseShardingValue) {
              for (String s : collection) {
                   Integer mod= Integer.parseInt( preciseShardingValue.getValue())%2;
                  if (s.endsWith( mod.toString())) {
                      return s;
                  }
                  continue;
              }
              return "sys_user";
          }
      
          @Override
          public Collection<String> doSharding(Collection<String> collection, RangeShardingValue<String> rangeShardingValue) {
              return null;
          }
      
          @Override
          public void init() {
      
          }
      
          @Override
          public String getType() {
              return "MOD1";
          }
      }
      

      经过改造,再运行,自定义的分片算法完成了!

      相关源码查看我的

      gitee项目

    如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^
    评论

报告相同问题?

问题事件

  • 创建了问题 4月30日

悬赏问题

  • ¥15 is not in the mmseg::model registry。报错,模型注册表找不到自定义模块。
  • ¥15 安装quartus II18.1时弹出此error,怎么解决?
  • ¥15 keil官网下载psn序列号在哪
  • ¥15 想用adb命令做一个通话软件,播放录音
  • ¥30 Pytorch深度学习服务器跑不通问题解决?
  • ¥15 部分客户订单定位有误的问题
  • ¥15 如何在maya程序中利用python编写领子和褶裥的模型的方法
  • ¥15 Bug traq 数据包 大概什么价
  • ¥15 在anaconda上pytorch和paddle paddle下载报错
  • ¥25 自动填写QQ腾讯文档收集表