문제

I have an entity that is join entity between Notification and User:

class NotificationRecipient implements Serializable {
    Notification notification

    User recipientUser

    static mapping = {
        table 'notification_recipient'
        version false

        notification cascade: 'all'
        recipientUser cascade: 'all'
        id generator: 'assigned', composite: ['notification', 'recipientUser']
    }
}

I want to create query that receive all notifications assigned to the specified user, but I want notification field to be populated to avoid N+1 selects while iterate over result (1 query for retreive list and one select per each notification field access with default lazy loading) as mentioned http://grails.org/doc/2.3.7/guide/single.html#criteria in Querying with Eager Fetching section.

I don't want to change mapping and set notification to lazy: false, but specify it in query (http://grails.org/doc/2.3.7/guide/single.html#fetchingDSL).

My query is (as docs says):

def resut = NotificationRecipient.createCriteria().list(options?.params ?: [:]) {
    eq("recipientUser.id", userId)
    join 'notification'
}

but still N+1 queries are generated.

I have also tried with setting Fetch mode:

NotificationRecipient.createCriteria().list(options?.params ?: [:]) {
    eq("recipientUser.id", userId)
    fetchMode "notification", FetchMode.JOIN
}

without success.

Can you explain me this behaviour of Grails?

도움이 되었습니까?

해결책

Unfortunalelly it is a Hibernate or Grails bug:

http://jira.grails.org/browse/GRAILS-9285

The solution is remove compound primary key id generator: 'assigned', composite: ['notification', 'recipientUser'] .

For compoun primary key joins doesn't work. Also order by is not working properly.

다른 팁

Have you tried using:

NotificationRecipient.findAllByRecepientUser(user, [fetch:[notification:'eager']])

A similar request works great (without the N+1) on my system.

I would also check if there are lazy fetched parameters on Notification (the Notification is loaded eagerly, but some properties in notifications are not simple types but Domain objects that need to be lazy loaded).

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top