Version:
* Spring Boot v2.2.7 * Hibernate v5.4.15.Final * {{spring-data-jpa-entity-graph}} v2.2.8
I have the following {{@Entity}} in my application.
{code:java}@Entity(name="DemoAccount") @Table(name="staff") @Getter @Setter @FieldNameConstants @NoArgsConstructor public class Account { @Id @GeneratedValue(strategy=GenerationType.IDENTITY) protected Long id; @Column(name="username", nullable=false) private String userId; private String name;
@ManyToOne(fetch=FetchType.LAZY) @LazyToOne(LazyToOneOption.NO_PROXY) @LazyGroup("nationality") @JoinColumn(name="nationality", referencedColumnName="code") private Nationality nationality; }
@Entity(name="DemoNationality") @Table(name="nationality ") @Getter @Setter @FieldNameConstants @NoArgsConstructor public class Nationality { @Id @GeneratedValue(strategy=GenerationType.IDENTITY) protected Long id; @Column(name="code", nullable=false) private String code; private String name; }{code}
I'm using the following {{@Repository}} to look for {{Account}}.
{code:java}@Repository public interface AccountRepo extends EntityGraphJpaRepository<Account, Long> { Optional<Account> findByUserId(String userId, EntityGraph entityGraph); }{code}
My test endpoint contains a simple method.
{code:java}@CustomerTransactional @GetMapping("/profile") public void testProfile(@RequestParam String userId) { Optional<Account> account = accountRepo.findByUserId(userId, EntityGraphs.create(Account.Fields.nationality)); if (account.isPresent()) { System.out.println(account.get().getName()); System.out.println(account.get().getNationality().getName()); } }{code}
When I execute this endpoint, this is what I'm seeing in the log.
{code:java}2020-05-24 16:18:26,492 DEBUG [http-nio-9000-exec-1] org.hibernate.SQL : /* select generatedAlias0 from DemoAccount as generatedAlias0 where generatedAlias0.userId=:param0 */ select account0_.id as id1_61_0_, nationalit1_.id as id1_35_1_, account0_.name as name4_61_0_, account0_.username as username6_61_0_, nationalit1_.code as code2_35_1_, nationalit1_.name as name4_35_1_ from staff account0_ left outer join nationality nationalit1_ on account0_.nationality=nationalit1_.code where account0_.username=? 2020-05-24 16:18:26,492 TRACE [http-nio-9000-exec-1] org.hibernate.type.descriptor.sql.BasicBinder : binding parameter [1] as [VARCHAR] - [90000010] Edgar Rey Tann 2020-05-24 16:18:26,506 DEBUG [http-nio-9000-exec-1] org.hibernate.SQL : /* sequential select com.ft.demo.db.customer.domain.Account */ select account_.nationality as nationa22_61_ from staff account_ where account_.id=? 2020-05-24 16:18:26,507 TRACE [http-nio-9000-exec-1] org.hibernate.type.descriptor.sql.BasicBinder : binding parameter [1] as [BIGINT] - [660] Indonesian{code}
As you can see, in the middle of the account name and the nationality name, there's an extra query just to select the {{ nationality }} field. It means if I have 50 records, 50 additional queries got executed. May I know how I can fix this behaviour?
Below is what I used in pom.xml to activate Hibernate Bytecode Enhancer
{code:java}<build> <plugins> <plugin> <groupId>org.hibernate.orm.tooling</groupId> <artifactId>hibernate-enhance-maven-plugin</artifactId> <version>${hibernate.version}</version> <executions> <execution> <configuration> <failOnError>true</failOnError> <enableLazyInitialization>true</enableLazyInitialization> <enableDirtyTracking>true</enableDirtyTracking> <enableAssociationManagement>true</enableAssociationManagement> </configuration> <goals> <goal>enhance</goal> </goals> </execution> </executions> </plugin> </plugins> </build>{code} |
|