Grails: multiple relationships between two domain objects

Let say you have two domain objects, Person and Post, and you want these kind of relationships in your project:

1. Person can write many Posts. (one-to-many relationship between Person and Post)

2. A Person can like many Posts, and particular Post can be liked by many Persons. (many-to-many relationship because a particular Post could be liked by many Persons, and each Person can like many Posts)

here is what you can do without having to create another domain class, Like.

Person Class

class Person{
   String username
   static hasMany = [posts: Post, likes: Post]
   static mappedBy = [posts: "person", likes: "personLikes"]
}

Post Class

class Post{
   String content
   Person person
   static hasMany = [personsLike: Person]
   static belongsTo = [Person]
}

Integration Spec Test

class FavouriteSpec extends Specification{
       def "User can like post and each post has many likes"() {

        given: "A user with a set of post"
        def joe = new Person(username: 'joe')
        def iqbal = new Person(username: 'iqbal')
        def julia = new Person(username: 'julia')

        def post1 = new Post(title: "First", content: "First post...")
        def post2 = new Post(title: "Second", content: "Second post...")
        def post3 = new Post(title: "Third", content: "Third post...")
        def post4 = new Post(title: "Fourth", content: "Fourth post...")

        joe.addToPosts(post1)
        joe.addToPosts(post2)
        joe.addToPosts(post3)
        iqbal.addToPosts(post4)

        when: "joe likes all his post, iqbal likes his post and post 1, julia likes post 4"
        joe.addToLikes(post1)
        joe.addToLikes(post2)
        joe.addToLikes(post3)
        iqbal.addToLikes(post4)
        iqbal.addToLikes(post1)
        julia.addToLikes(post4)
        julia.addToLikes(post1)
        julia.addToLikes(post3)

        then:
        3 == joe.likes.size()
        2 == iqbal.likes.size()
        3 == julia.likes.size()

        3 == post1.personsLike.size()
        1 == post2.personsLike.size()
        2 == post3.personsLike.size()
        2 == post4.personsLike.size()
    }
}

keywords: grails likes domain design, Facebook like in grails, grails favorite plugin

Leave a comment