关于spring-data与elasticsearch的使用,自定义repository

之前没有使用过spring-data,关于spring-data有很多很棒的设计,例如仅仅只需要声明一个接口就行,你甚至都不需要去实现,spring-data有内置默认的实现类,基本就上完成绝大多数对单表的操作

然后是因为使用es,也想着用spring-data来集成,遇到自定义的repository的问题,网上找到大多数文字讲的都不是很清晰,在一番折腾了之后,把自己的做法分享一下

下面是我接口和类的UML图

其中 ICustomerRepository 是我打算实现自定义的repository的接口,这里根据spring-data的约定,后缀都是Repository

ICustomerRepositoryCustom是我要实现的自定义的方法,例如我想在查询后根据业务什么的做一些转换和过滤,在这个例子中,就统一在doSomeThind中了

最终的重点来了,对于自定义的方法,spring-data是需要我们来告诉它,是由于哪个类来实现,而ICustomerRepository同时也继承了ICustomerRepositoryCustom接口,如果这个时候,实现类的命令是以 ICustomerRepositoryCustomImpl来命名的,并去实现ICustomerRepositoryCustom,那么在方法调用中,会报告一个property exception的错误,说找不到doSomeThing这个属性,因为这个问题搞了很久,后面去结合别人的文章,总算是晓得了

你需要实现的接口是ICustomerRepositoryCustom没有错,但命名上需要是ICustomerRepositoryImpl,否则spring-data会找不到它的实现类,就默认这个方法是你传入的Bean的属性,以下是具体的代码,仅供参考

@Repository
public interface ICustomerRepository extends ElasticsearchRepository<User, String>
        , ICustomerRepositoryCustom<User, String> {

    List<User> findByLastName(String lastName);

    List<User> findByFirstName(String firstName);

    List<User> findUsersByAgeBetweenOrderByBirthdayDesc(Integer min, Integer max);

}


public interface ICustomerRepositoryCustom<T, ID extends Serializable> {

    void doSomeThing();

}


@Component
public class ICustomerRepositoryImpl implements ICustomerRepositoryCustom<User,String> {

    @Override
    public void doSomeThing() {
        System.out.println("我是自定义的一个实现方法");
    }
}


// 这个bean根据你是要集成什么数据库会有不同,这里我集成的是es,因此声明索引是什么,以及各个字段
@Document(indexName = "user")
public class User {

    @Id
    private String id;

    @Field
    private String firstName;

    @Field
    private String lastName;

    @Field
    private Integer age;

    @Field
    private Date birthday = new Date();

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String firstName) {
        this.firstName = firstName;
    }

    public String getLastName() {
        return lastName;
    }

    public void setLastName(String lastName) {
        this.lastName = lastName;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }

    public Date getBirthday() {
        return birthday;
    }

    public void setBirthday(Date birthday) {
        this.birthday = birthday;
    }
}

经过上面的折腾后,你就可以很潇洒的在业务层这样调用了

    @Autowired
    private ICustomerRepository customerRepository;

    @RequestMapping(value = "/user/{name}", method = RequestMethod.PUT)
    public User put(@PathVariable String name) {
        User u = new User();
        u.setFirstName(name);
        u.setLastName("tom");
        u.setAge(random.nextInt(99));
        // 这个是spring-data默认给我们实现的
        customerRepository.save(u);
        // 这个是我们自定义的方法
        customerRepository.doSomeThing();
        return u;
    }
posted @ 2019-05-23 09:09  myCodeLikeShit  阅读(5917)  评论(0编辑  收藏  举报