JPA规格通用类型类

发布于 2025-01-21 22:38:45 字数 5771 浏览 0 评论 0原文

目前,我正在使用规格和标准构建器进行预先搜索项目,我有多个实体我想创建一个通用的类规范构建器。我的问题,可以做到吗?

实体示例

@Entity
@Table(name = "marcas")
public class Brand implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    @Column(name = "nombre")
    private String name;
    @Enumerated(EnumType.STRING)
    @Column(name = "tipo_marca")
    private Brandtype brandtype;
    @Column(name = "fecha_creacion")
    private LocalDateTime creationDate;
    @Column(name = "fecha_actalizacion")
    private LocalDateTime updateDate;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Bike> bikes;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Model> models;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Accesorie> accesories;

    public Brand() {
    }

    public Brand(Integer id, String name, Brandtype brandtype) {
        this.id = id;
        this.name = name;
        this.brandtype = brandtype;
    }

    public Integer getId() {
        return id;
    }

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

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Brandtype getBrandtype() {
        return brandtype;
    }

    public void setBrandtype(Brandtype brandtype) {
        this.brandtype = brandtype;
    }

    public Set<Bike> getBikes() {
        return bikes;
    }

    public void setBikes(Set<Bike> bikes) {
        this.bikes = bikes;
    }

    public Set<Model> getModels() {
        return models;
    }

    public void setModels(Set<Model> models) {
        this.models = models;
    }

    public Set<Accesorie> getAccesories() {
        return accesories;
    }

    public void setAccesories(Set<Accesorie> accesories) {
        this.accesories = accesories;
    }

    public LocalDateTime getCreationDate() {
        return creationDate;
    }

    public void setCreationDate(LocalDateTime creationDate) {
        this.creationDate = creationDate;
    }

    public LocalDateTime getUpdateDate() {
        return updateDate;
    }

    public void setUpdateDate(LocalDateTime updateDate) {
        this.updateDate = updateDate;
    }

    @PrePersist
    public void beforeCreate(){
        this.creationDate = LocalDateTime.now();
    }

    @PreUpdate
    public void beforeUpdate(){
        this.updateDate = LocalDateTime.now();
    }

    @Override
    public String toString() {
        return "Brand{" +
                "id=" + id +
                ", name='" + name + '\'' +
                ", brandtype=" + brandtype+
                '}';
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Brand brand = (Brand) o;
        return id.equals(brand.id) && name.equals(brand.name);
    }

    @Override
    public int hashCode() {
        return Objects.hash(id, name);
    }
}

回关示例

@Repository
public interface BrandRepository extends PagingAndSortingRepository <Brand, Integer>, JpaSpecificationExecutor<Brand> {

}

搜索标准类:

public class SearchCriteria {
    private String key;
    private String operation;
    private Object value;

    public SearchCriteria() {
    }

    public SearchCriteria(String key, String operation, Object value) {
        this.key = key;
        this.operation = operation;
        this.value = value;
    }

    public String getKey() {
        return key;
    }

    public void setKey(String key) {
        this.key = key;
    }

    public String getOperation() {
        return operation;
    }

    public void setOperation(String operation) {
        this.operation = operation;
    }

    public Object getValue() {
        return value;
    }

    public void setValue(Object value) {
        this.value = value;
    }
}

这是类规范:

public class BrandSpecification implements Specification<Brand>{

    private SearchCriteria criteria;

    public BrandSpecification(SearchCriteria searchCriteria) {
        this.criteria = searchCriteria;
    }

    @Override
    public Predicate toPredicate(Root<Brand> root, CriteriaQuery<?> query, CriteriaBuilder builder) {
        if (criteria.getOperation().equalsIgnoreCase(">")) {
            
            return builder.greaterThanOrEqualTo(
                    root.<String> get(criteria.getKey()), criteria.getValue().toString());

        }
        else if (criteria.getOperation().equalsIgnoreCase("<")) {
            return builder.lessThanOrEqualTo(
                    root.<String> get(criteria.getKey()), criteria.getValue().toString());
        }
        else if (criteria.getOperation().equalsIgnoreCase(":")) {
            if (root.get(criteria.getKey()).getJavaType() == String.class) {
                return builder.like(
                        root.<String>get(criteria.getKey()), "%" + criteria.getValue() + "%");
            } else {
                return builder.equal(root.get(criteria.getKey()), criteria.getValue());
            }
        }
        return null;
    }

    public SearchCriteria getCriteria() {
        return criteria;
    }

    public void setCriteria(SearchCriteria criteria) {
        this.criteria = criteria;
    }
}

我想转换为通用,以便我可以重新使用代码并且不需要多次重写,我可以有类似的东西:public> Public class类GenericsPecification insterments实施规范&lt; e&gt; {}

I'm currently building a advance search for a project using Specifications and Criteria Builder, I have multiple entities that I would like to create a generic class Specification builder. My question, is it possible to do it?

Entity example

@Entity
@Table(name = "marcas")
public class Brand implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    @Column(name = "nombre")
    private String name;
    @Enumerated(EnumType.STRING)
    @Column(name = "tipo_marca")
    private Brandtype brandtype;
    @Column(name = "fecha_creacion")
    private LocalDateTime creationDate;
    @Column(name = "fecha_actalizacion")
    private LocalDateTime updateDate;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Bike> bikes;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Model> models;

    @OneToMany(
            mappedBy = "brand",
            fetch = FetchType.LAZY
    )
    private Set<Accesorie> accesories;

    public Brand() {
    }

    public Brand(Integer id, String name, Brandtype brandtype) {
        this.id = id;
        this.name = name;
        this.brandtype = brandtype;
    }

    public Integer getId() {
        return id;
    }

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

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Brandtype getBrandtype() {
        return brandtype;
    }

    public void setBrandtype(Brandtype brandtype) {
        this.brandtype = brandtype;
    }

    public Set<Bike> getBikes() {
        return bikes;
    }

    public void setBikes(Set<Bike> bikes) {
        this.bikes = bikes;
    }

    public Set<Model> getModels() {
        return models;
    }

    public void setModels(Set<Model> models) {
        this.models = models;
    }

    public Set<Accesorie> getAccesories() {
        return accesories;
    }

    public void setAccesories(Set<Accesorie> accesories) {
        this.accesories = accesories;
    }

    public LocalDateTime getCreationDate() {
        return creationDate;
    }

    public void setCreationDate(LocalDateTime creationDate) {
        this.creationDate = creationDate;
    }

    public LocalDateTime getUpdateDate() {
        return updateDate;
    }

    public void setUpdateDate(LocalDateTime updateDate) {
        this.updateDate = updateDate;
    }

    @PrePersist
    public void beforeCreate(){
        this.creationDate = LocalDateTime.now();
    }

    @PreUpdate
    public void beforeUpdate(){
        this.updateDate = LocalDateTime.now();
    }

    @Override
    public String toString() {
        return "Brand{" +
                "id=" + id +
                ", name='" + name + '\'' +
                ", brandtype=" + brandtype+
                '}';
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Brand brand = (Brand) o;
        return id.equals(brand.id) && name.equals(brand.name);
    }

    @Override
    public int hashCode() {
        return Objects.hash(id, name);
    }
}

Reposotory example

@Repository
public interface BrandRepository extends PagingAndSortingRepository <Brand, Integer>, JpaSpecificationExecutor<Brand> {

}

Search Criteria class:

public class SearchCriteria {
    private String key;
    private String operation;
    private Object value;

    public SearchCriteria() {
    }

    public SearchCriteria(String key, String operation, Object value) {
        this.key = key;
        this.operation = operation;
        this.value = value;
    }

    public String getKey() {
        return key;
    }

    public void setKey(String key) {
        this.key = key;
    }

    public String getOperation() {
        return operation;
    }

    public void setOperation(String operation) {
        this.operation = operation;
    }

    public Object getValue() {
        return value;
    }

    public void setValue(Object value) {
        this.value = value;
    }
}

And this is the class Specification:

public class BrandSpecification implements Specification<Brand>{

    private SearchCriteria criteria;

    public BrandSpecification(SearchCriteria searchCriteria) {
        this.criteria = searchCriteria;
    }

    @Override
    public Predicate toPredicate(Root<Brand> root, CriteriaQuery<?> query, CriteriaBuilder builder) {
        if (criteria.getOperation().equalsIgnoreCase(">")) {
            
            return builder.greaterThanOrEqualTo(
                    root.<String> get(criteria.getKey()), criteria.getValue().toString());

        }
        else if (criteria.getOperation().equalsIgnoreCase("<")) {
            return builder.lessThanOrEqualTo(
                    root.<String> get(criteria.getKey()), criteria.getValue().toString());
        }
        else if (criteria.getOperation().equalsIgnoreCase(":")) {
            if (root.get(criteria.getKey()).getJavaType() == String.class) {
                return builder.like(
                        root.<String>get(criteria.getKey()), "%" + criteria.getValue() + "%");
            } else {
                return builder.equal(root.get(criteria.getKey()), criteria.getValue());
            }
        }
        return null;
    }

    public SearchCriteria getCriteria() {
        return criteria;
    }

    public void setCriteria(SearchCriteria criteria) {
        this.criteria = criteria;
    }
}

I want to convert to generic so I can re use the code and dont need to rewrite it multiple times, can I have something like: public class GenericSpecification implements Specification<E>{}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

狠疯拽 2025-01-28 22:38:45

您可以执行以下操作:

public class AppSpecification<T> implements Specification<T>{

private SearchCriteria criteria;

public AppSpecification(SearchCriteria searchCriteria) {
    this.criteria = searchCriteria;
}

@Override
public Predicate toPredicate(Root<T> root, CriteriaQuery<?> query, CriteriaBuilder builder) {
    if (criteria.getOperation().equalsIgnoreCase(">")) {

        return builder.greaterThanOrEqualTo(
                root.<T> get(criteria.getKey()), criteria.getValue().toString());

    }
    else if (criteria.getOperation().equalsIgnoreCase("<")) {
        return builder.lessThanOrEqualTo(
                root.<T> get(criteria.getKey()), criteria.getValue().toString());
    }
    else if (criteria.getOperation().equalsIgnoreCase(":")) {
        if (root.get(criteria.getKey()).getJavaType() == String.class) {
            return builder.like(
                    root.<T>get(criteria.getKey()), "%" + criteria.getValue() + "%");
        } else {
            return builder.equal(root.get(criteria.getKey()), criteria.getValue());
        }
    }
    return null;
}

然后,您可以按以下方式启动课程:

var brandSpecification = new AppSpecification<Brand>(searchCriteria);

You can do the following:

public class AppSpecification<T> implements Specification<T>{

private SearchCriteria criteria;

public AppSpecification(SearchCriteria searchCriteria) {
    this.criteria = searchCriteria;
}

@Override
public Predicate toPredicate(Root<T> root, CriteriaQuery<?> query, CriteriaBuilder builder) {
    if (criteria.getOperation().equalsIgnoreCase(">")) {

        return builder.greaterThanOrEqualTo(
                root.<T> get(criteria.getKey()), criteria.getValue().toString());

    }
    else if (criteria.getOperation().equalsIgnoreCase("<")) {
        return builder.lessThanOrEqualTo(
                root.<T> get(criteria.getKey()), criteria.getValue().toString());
    }
    else if (criteria.getOperation().equalsIgnoreCase(":")) {
        if (root.get(criteria.getKey()).getJavaType() == String.class) {
            return builder.like(
                    root.<T>get(criteria.getKey()), "%" + criteria.getValue() + "%");
        } else {
            return builder.equal(root.get(criteria.getKey()), criteria.getValue());
        }
    }
    return null;
}

then you can initiate the class as follows:

var brandSpecification = new AppSpecification<Brand>(searchCriteria);
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文