Соединить две таблицы по условию с CriteriaBuilder
У меня есть таблицы, в которых я сохраняю разные автомобили, в таблице цен я сохраняю историю цен в зависимости от региона, в котором находится продавец. Все работает нормально, но как я могу получить все машины для продавца только с ценовой историей для этого автомобиля?
Автомобильный стол
@Entity
@Table(name = "car")
public class Car {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Column(unique = true)
private String numberPlate;
private String carName;
...
@Lob
@Column(columnDefinition="mediumblob")
private byte[] image;
private float lastPrise;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "car")
private List<ProductPrice> carPrices;
}
Таблица цен
@Entity
@Table(name = "price")
@EntityListeners({ProductPrice.WritableEntityListener.class})
public class CarPrice {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Temporal(TemporalType.TIMESTAMP)
@Column(nullable = false)
private Date created;
@Column(nullable = false)
private String createdBy;
private float price;
@OneToOne
private Region region;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "car_id", nullable = false)
private Car car;
private Date priceDate;
private Date priceDateFrom;
private Date priceDateTo;
}
Таблица регионов
@Entity
@Table(name = "region")
public class Region {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private Long regionId;
private String regionName;
}
Как я могу получить все машины для региона (по идентификатору региона).
Если я использую следующее заявление SQL я получу результат, который я ожидал
SELECT DISTINCT DATE(pp.priceDate) AS datePrice, c.id, c.CarName, c.numberPlate, c.description, c.lastPrise, pp.price, g.name, pp.grocery_id
FROM car p, region g
JOIN price pp
WHERE
c.id=pp.product_id
AND pp.region_id=g.id
AND pp.region_id=570
ORDER BY c.name, pp.region_id, datePrice;
но как я могу построить это с CriteriaBuilder.
Следующий фрагмент показывает мое решение, но я получаю не только историю цен для выбранного region_id, но и для всех регионов.
public List<Car> getCarAndLatestPrice(Long id) {
CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
CriteriaQuery<Car> qry = cb.createQuery(Car.class);
Root<Car> car = qry.from(Car.class);
//Root<Region> region = qry.from(Region.class);
Join<Car, ProductPrice> price = car.join("productPrices");
qry.distinct(true);
qry.select(car);
qry.orderBy(cb.asc(car.get("name")));
List<Predicate> conditions = new ArrayList<>();
conditions.add(cb.equal(price.get("region"), id));
TypedQuery<Car> typedQuery = getEntityManager().createQuery(qry
.select(car)
.where(conditions.toArray(new Predicate[]{}))
.distinct(true));
List<Car> productList = typedQuery.getResultList();
return productList;
}
Может быть, у кого-то есть похожая проблема, и она может предложить мне решение.