0

In my project, I am using Spring Data JPA and extend the JpaRepository interface for my data fetching class.

OrganizationMaster class :

  @Entity
  @Table(name="organization_master")
  public class OrganizationMaster  {

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    @Column(name="organization_id")
    private int organizationId;

    @OneToMany(mappedBy="organizationMaster")
        private List<CompanyMaster> companyMasters;
    }

CompanyMaster Class:

Entity
@Table(name="company_master")
public class CompanyMaster {

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    @Column(name="company_id")
    private int companyId;


    @ManyToOne
    @JoinColumn(name="organization_id")
    private OrganizationMaster organizationMaster;
}

My Controller

@RequestMapping(value = "/GetOrganization", method = RequestMethod.GET)
    public
    @ResponseBody
    List<OrganizationMaster> getOrganization(){
       return organizationService.getOrganization();
    }

OrganizationService:

public interface OrganizationService {
   List<OrganizationMaster> getOrganization();
}

OrganizationServiceImpl:

@Service
public class OrganizationServiceImpl implements OrganizationService{
    @Autowired
    private OrganizationDao organizationDao;
    @Override
    public List<OrganizationMaster> getOrganization() {
        return organizationDao.findAll();
    }
}

OrganizationDao Interface:

public interface OrganizationDao extends JpaRepository<OrganizationMaster,Long> {
}

My Output Response is: [{"organizationId":5,"companyMasters":[{"companyId":29},{"companyId":30}]}]

But my need is [{"organizationId":5}]

When I am trying to get data from the organization master using findall() method it also fetches data from the company master based on the relationship. How can I achieve lazy fetching (get data only from organization master) using spring data JpaRepository

6
  • No, it doesn't. It's not findAll() that fetches the CompanyMaster entities. It's what you're doing with the loaded OrganizationMaster entities after you've loaded them. lazy loading doesn't mean that JPA won't load them, ever. It means that it will load them only when the code actually needs to use them. So, if for example you have System.out.println(organization.getCompanyMasters()), it will load them at that time, because printing a list means printing every element of the list, and to print an element, you need to have that element, and to have that element, you need to load it. Commented Nov 28, 2018 at 6:59
  • when I use System.out.println(organization) it also prints the companyMaster values. Commented Nov 28, 2018 at 7:37
  • And what is the toString() method of OrganizationMaster? Commented Nov 28, 2018 at 7:41
  • I use only getters and setters and no toString() method for OrganizationMaster Commented Nov 28, 2018 at 7:46
  • 1
    Post the code if you want us to explain what it does and why it lazy-loads the companyMasters. But anyway, the simple fact that you ask Spring to serialize the OarganizationMaster to JSON will force the lazy-loading, since you didn't configure Jackson to ignore the companyMasters. Commented Nov 28, 2018 at 7:49

2 Answers 2

3

All XToOne associations are default EAGER. You have a bidirectional relationship, so you should use FetchType.LAZY on your @ManyToOne side.

@ManyToOne(fetch = FetchType.LAZY)

Also if you use any serializer (like json serializer) when it serialize it calls getter methods and it may causes to load lazy items unneccessarly.

Another consideration is while using Lombok, @Data annotation causes to load lazy items without need. So be careful when using Lombok.

So in your case, beacuse of you return entity itself, while serialization it serializes the child too, it causes to load lazly child entity.

You need to return a dto which represents only your parent entity to prevent serialization of child entity. If you call child with getter method, it laods lazly child entity from database.

Take a look for further information associations:

https://vladmihalcea.com/the-best-way-to-map-a-onetomany-association-with-jpa-and-hibernate/

Sign up to request clarification or add additional context in comments.

3 Comments

@ManyToOne(fetch = FetchType.LAZY) it also not working. Where to use @Data annotation
I see, like I said, you return the entity on your controller, so while serializing it serializes child relation too. So it loads childs lazy while serializing. It is obvious you can see child entity in your response.
You should convert your entity to a dto for preventing serialization of child entity.
-1

I believe this question is asked before!you can use this annotation:

@OneToMany( fetch = FetchType.LAZY )

read this article for better view in this point:

https://howtodoinjava.com/hibernate/lazy-loading-in-hibernate/

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.