Весна: правильное обращение с дочерней коллекцией - PullRequest
1 голос
/ 14 апреля 2020

Допустим, я управляю интернет-магазином. Я хочу иметь возможность добавлять и обновлять продукты через REST API.

Ожидаемый DTO будет выглядеть примерно так:

{
  "id": 1,
  "name": "iPhone 11 Pro",
  "price": 999,
  "pictures": [
    {
      "url": "http://image.com/image1.jpg",
      "description": "image 1"
    },
    {
      "url": "http://image.com/image2.jpg",
      "description": "image 2"
    }
  ]
}

При использовании JPA для этого потребуется 2 следующих объекта:

@Entity
public class Product {
  private Long id;

  private String name;

  private Integer price;

  @OneToMany(mappedBy="product")
  private List<ProductPicture> pictures;
}

@Entity
public class ProductPicture {
  private Long id;

  @ManyToOne
  private Product product;

  private String url;

  private String description;
}

Как обрабатывать обновление продукта? Во всех учебных пособиях / примерах кодов, которые я нахожу, это всегда очень простой c пример с одним объектом, у которого нет коллекции.

Я думаю о некоторых вариантах:

  • получить продукт из БД, очистите список «картинки» и заполните его, затем сохраните;
  • извлеките продукт из БД, итерируйте по всем изображениям, чтобы найти совпадения, затем удалите / добавьте то, что нужно, затем сохраните;
  • может быть, есть магия Spring / Hibernate c для этого?

Мне не нравятся 2 первых.

Я почти собираюсь выбрать для базы данных SQL, поскольку в этом случае использования будет намного проще ... даже если это, вероятно, не веская причина.

Кроме того, я не одобряю использование выделенной конечной точки для это (например, POST или DELETE для /products/1/pictures).

Не могли бы вы поделиться примером кода для обработки обновления с помощью Spring / Hibernate? Спасибо!

1 Ответ

0 голосов
/ 17 апреля 2020

Я наконец-то использовал аннотации @Embeddable и @ElementCollection, которых я не знал, что идеально подходит для того, что я хотел сделать.

@Entity
public class Product {
  private Long id;

  private String name;

  private Integer price;

  @ElementCollection(fetch = FetchType.EAGER)
  private List<ProductPicture> pictures;
}

@Embeddable
public class ProductPicture {
  private String url;

  private String description;
}

Таким образом, обновление супер-легкий:

Product dbProduct = productRepository.findById(product.getId()).get();
// ...
dbProduct.setPictures(product.getPictures());
productRepository.save(dbProduct);
...