20 Ağustos 2023 Pazar

SpringData JPA @EntityGraph.type FETCH + @NamedEntityGraph Kullanımı - N+1 Select Problem İçindir

Giriş
Açıklaması şöyle. Yani  @NamedEntityGraph.attributeNodes anotasyonu ile belirtilenler EAGER yüklenir. Geri kalan her şey LAZY yüklenir.
..., attributes that are specified by attribute nodes of the entity graph are treated as FetchType.EAGER and attributes that are not specified are treated as FetchType.LAZY

Örnek - @NamedEntityGraph.attributeNodes 
Şöyle yaparız. Burada Publication sınıfı ve ona ait Article sınıfları EAGER yükleniyor.
@Entity
@Table(name = "publication")
@NamedEntityGraph(name="publication-articles-graph",
  attributeNodes = @NamedAttributedNode(value ="articles"))
public class Publication {
  ...
  @OneToMany(cascade = CascadeType.ALL)
  @JoinColumn(name = "publicationId")
  private List<Article> articled;
}

public interface PublicationRepository extends JpaRepository<Publication,String> {
  @EntityGraph(type = EntityGraph.EntityGraphType.FETCH,
    value = "publication-articles-graph")
  List<Publication> findByCategory(String category);
}
Eğer @NamedEntityGraph kullanmak istemiyorsak şöyle yaparız. Burada  @EntityGraph.attributePaths kullanılıyor
public interface PublicationRepository extends JpaRepository<Publication,String> { @EntityGraph(type = EntityGraph.EntityGraphType.FETCH, attributePaths = "articles") List<Publication> findByCategory(String category); }
Çıkan SQL şöyledir
SELECT * FROM publication LEFT OUTER JOIN article ON publication.publication_id = article.publication_id WHERE publication.category = 'technology'
Örnek
Şöyle yaparız. Burada Book ve ona ait Author nesneleri EAGER yüklenir
@Entity @NamedEntityGraph( name = "Book.author", attributeNodes = @NamedAttributeNode("author") ) public class Book { @ManyToOne private Author author; // ... } @Repository public interface BookRepository extends JpaRepository<Book, Long> { @EntityGraph("Book.author") List<Book> findAll(); }

Hiç yorum yok:

Yorum Gönder