Search code examples
node.jsormprismaprisma2

How to prevent Prisma from showing redundant/ unnecessarly nested properties in Many-To-Many-Relationship query?


I try to retrieve a user and the organisations he is a member of. The array with the organisations contains redundant/ unnecessarly nested properties.

I have the following Setup.

    model Organization {   
    id            Int   @id @default(autoincrement())   
    name          String   
    ownerId       Int   
    owner         User   
    
    model User {
      id                 Int                     @id @default(autoincrement())
      email              String                  @unique
      password           String
      organizations      MembersInOrganization[]
      ownedOrganizations Organization[]
    }
    
    model MembersInOrganization {
      organization   Organization @relation(fields: [organizationId], references: [id])
      organizationId Int
      user           User         @relation(fields: [userId], references: [id])
      userId         Int
    
      @@id([organizationId, userId])
    }            

I want to retrieve a user and the organizations he is a member of. The result of the following query is something like that:

    let user = await prisma.user.findUnique({
                where: {
                    id:  verified.sub
                },
                 include: {
                    organizations: {
                        select: {
                            organization: true
                        }
                    }
                } 
            })        
    {
      "id": 1,
      "email": "someting@gmail.com",
      "password": "HASHED_PASSWORD",
      "organizations": [
        {
          "organization": {
            "id": 1,
            "name": "lol",
            "ownerId": 1
          }
        },
        {
          "organization": {
            "id": 2,
            "name": "Cool",
            "ownerId": 1
          }
        },
        {
          "organization": {
            "id": 3,
            "name": "Very cool",
            "ownerId": 1
          }
        },
      ]
    }

Now my question how can I prevent the redundant property name in the array? So that the result looks like this:

    {
      "id": 1,
      "email": "someting@gmail.com",
      "password": "HASHED_PASSWORD",
      "organizations": [
        {
            "id": 1,
            "name": "lol",
            "ownerId": 1
          
        },
        {
            "id": 2,
            "name": "Cool",
            "ownerId": 1
          
        },
        {
       
            "id": 3,
            "name": "Very cool",
            "ownerId": 1
          
        },
      ]
    }

Solution

  • Based on your schema file, it won't be possible to remove the organizations keyword natively. It would need further processing by looping over the organizations array.

    You could achieve the response by using below query:

      let user = await prisma.user.findUnique({
        where: {
          id: 2,
        },
        include: {
          organizations: {
            select: {
              organization: {
                select: {
                  name: true,
                  ownerId: true,
                  id: true,
                },
              },
            },
          },
        },
      });
    
      //@ts-ignore
      user.organizations = user?.organizations.map((org) => {
        //@ts-ignore
        return (org = { ...org.organization });
      });
    
      console.log(JSON.stringify(user, null, 2));
    

    Here's the sample response

    {
      "id": 2,
      "email": "t@g.com",
      "password": "123456",
      "organizations": [
        {
          "name": "test",
          "ownerId": 2,
          "id": 1
        }
      ]
    }