Spring Mongo我是如何一步步创造了最长方法名记录的

41 阅读3分钟

背景

项目有些数据使用mongodb 存储的,Spring data mongo给我们封装了许多通用的增删查改功能,我们继承MongoRepository 就自动包含了常见的增删查改。更神奇的是它可以根据方法名,自动转换为查询条件,比如根据名称查询,我们只需要定义一个方法(如下面实例代码),然后就能直接使用了,第一次接触时,简直惊为天人,这太好用了,MyBatis 还要写SQL。这个真正的见名知义

图片

public interface UserRepository extends MongoRepository<User,String> {

    List<User> findByName(String name);
  
}

如果多个条件 直接And 连起来, 还支持Like , GreaterThan , LessThan ,Order By ,Top 等关键字,简直不要太方便。

使用泛滥

对于简单的查询,确实很好用,但是有些复杂的查询,举个例子,用户信息User 类,比如某家餐厅现在有活动给年满18,张姓客户,会员积分前5 的可以打5折,为了实现这个需求,“我”写了个查询方法如下,写出来发现方法名称很长,可能我屏幕小,一个方法调用就出现滚动条了

@Data
public class User {
    @Id
    private String id;

    /**
     * 姓名
     */
    private String name;

    /**
     * 年龄
     */
    private int age;

    /**
     * 性别
     */
    private String gender;

    /**
     * 积分
     */
    private int memberPoint;

    /**
     * 城市
     */
    private String city;


}
   public interface UserRepository extends MongoRepository<User,String> {

    List<User> findByName(String name);

    List<User> findTop5ByNameLikeAndCityAndAgeGreaterThanOrderByMemberPoint(String name,String city,int age);

}
 List<User> selectUsers =   userRepository.findTop5ByNameLikeAndCityAndAgeGreaterThanOrderByMemberPoint("张","杭州",18);

继续迭代

接着老板给我说,这个姓氏来我们店比较少,有几个来过一次,积分很少就享受这个优惠,不合理,要我加上会员积分大于100的条件。为了不影响原来的方法我新写了一个方法,当然是在原来基础上改的。于是这个类又多了个方法

图片

public interface UserRepository extends MongoRepository<User,String> {

    List<User> findByName(String name);

    List<User> findTop5ByNameLikeAndCityAndAgeGreaterThanOrderByMemberPoint(String name,String city,int age);

    List<User> findTop5ByNameLikeAndCityAndAgeGreaterThanOrderAndMemberPointGreaterThanByMemberPoint(String name,String city,int age,int memberPoint);
}

需求再次变更

老板说Top 5有点亏, 改成Top 3 。同样之前的方法可能由于被调用了,所以又新写了一个,于是类变成这样。

图片

public interface UserRepository extends MongoRepository<User,String> {

    List<User> findByName(String name);

    List<User> findTop5ByNameLikeAndCityAndAgeGreaterThanOrderByMemberPoint(String name,String city,int age);

    List<User> findTop5ByNameLikeAndCityAndAgeGreaterThanOrderAndMemberPointGreaterThanByMemberPoint(String name,String city,int age,int memberPoint);

    List<User> findTop3ByNameLikeAndCityAndAgeGreaterThanOrderAndMemberPointGreaterThanByMemberPoint(String name,String city,int age,int memberPoint);
}

后来为了吸引用户老板又改成Top 10 ,还加了一些条件,然后我的查询方法又更加长了,看起来都差不多,就这样反反复复多次,我终于受不了, 虽然我们都知道MongoTemplate 可以自己组装查询条件,但谁也不愿意做第一个改变的人,终于我受不了了, 实在受不了方法名太长了,不换行或者拖动滚动条,完全不知道在调用什么方法

于是使用MongoTemplate 组装查询,不过也不好,总感觉担心Criteria 中字段拼写错误,导致查询失败。

 public List<User> queryByCondition(String name, List<String> citys, int age,int topN){

        Query query = new Query(Criteria.
                where("name").regex(name + ".*").and("city").in(citys).and("age").gt(age)).limit(topN).with(Sort.by("memberPoint"));

       return mongoTemplate.find(query, User.class);
    }

上面问题也可以在UserRepository 方法上使用Query 注解,这样方法名可以不按照拼接“属性条件” 格式,可以使用用户自定义的,不过@Query 写查询条件也比较恶心。

这时才十分想念Mybatis ,还是写Sql爽。

你们最长的方法名多长,有人写过80个字符的方法名吗?

扫码_搜索联合传播样式-白色版.png