0

In Laravel Lighthouse GraphQL, how can you retrieve the information from an intermediate "pivot" table?

Suppose I have Users and Roles in a belongsToMany relation:

type User {
  roles: [Role!]! @belongsToMany
}

type Role {
  users: [User!]! @belongsToMany
}

type Query {
    user(id: ID! @eq): User @find
    role(id: ID! @eq): Role @find
}

And also suppose that the intermediate table User_Role contains columns "created_at" and "tag_id".
How would I go about to include the "created_at" in my query?
How would I get the tag that the tag_id refers to?

Hendrik Jan
  • 4,396
  • 8
  • 39
  • 75

1 Answers1

8

I found out that you can do it like this:

First, make sure that the relation in the User model calls ->withPivot('created_at', 'tag_id'):

class User extends Model {
    public function roles(): BelongsToMany
    {
        return $this->belongsToMany(\App\Models\Role::class, 'User_Role')
                    ->using(User_Role::class) // only needed to retrieve the tag from the tag_id
                    ->withPivot('created_at', 'tag_id');
    } 
}

Create a class for the intermediate table that extends Pivot:

class User_Role extends Pivot
{
    public function tag(): BelongsTo
    {
        return $this->belongsTo(\App\Models\Tag::class, 'tag_id');
    }
}

Now change the GraphQL code as follows:

type User {
    id: ID!
    roles: [Role!] @belongsToMany
}

type Role {
    id: ID!
    pivot: UserRolePivot # this is where the magic happens
}

type UserRolePivot {
    created_at: Date!
    tag: Tag! @belongsTo
}

type Tag {
    id: ID!
    name: String!
}

And now you can query like this:

{
  users {
    id
    roles {
      id
      pivot {
        created_at
        tag {
          id
          name
        }
      }
    }
  }
}
Hendrik Jan
  • 4,396
  • 8
  • 39
  • 75
  • 1
    Thank you! Is there in the documentation / github issue ? And is there any way to change the name of the property, I would like to use "product_pivot" instead of "pivot" which is too generic – Sir Mishaa May 05 '21 at 16:01
  • 1
    It has been too long ago for me to know how I found my answer, or to know where to look. I guess that if you change my code to `type Role {id: ID! product_pivot: UserRolePivot}` you get what you want. – Hendrik Jan May 05 '21 at 17:51
  • @HendrikJan That doesn't work, singular or plural (i.e. `products_pivot`) – user110857 Jun 17 '21 at 21:33