Skip to content

Use real GraphQL query in home organization select

What does this MR do and why?

Related to #429999 (closed)

The grouptenant scale team is starting to build out an Organization MVC. For more information about what an "Organization" will be see https://docs.gitlab.com/ee/architecture/blueprints/organization/

In User Default organization setting (#419079 - closed) we built a dropdown that listed organizations for the "Home organization" setting. Because the GraphQL query was not available at the time we used a a mock GraphQL query. Now that GraphQL query for listing a user's organizations (#417892 - closed) has been closed we have access to the real query. This MR swaps the mock query for the real one.

Notes

Query plans

We added search support to the Organizations::Organization model. We are not yet adding records to the organization_users so I couldn't figure out a way to run the query to return actual records. Not sure how helpful these query plans are because of that. I asked about adding records to organization_users in https://gitlab.slack.com/archives/C01TQ838Y3T/p1701210892910009

Here are the before and after query plans

Before

https://console.postgres.ai/gitlab/gitlab-production-tunnel-pg12/sessions/24341/commands/77758

Query

SELECT
    "organizations".*
FROM
    "organizations"
    INNER JOIN "organization_users" ON "organizations"."id" = "organization_users"."organization_id"
WHERE
    "organization_users"."user_id" = 5413811
ORDER BY
    "organizations"."id" DESC
LIMIT 21

Plan

 Limit  (cost=3.91..3.92 rows=1 width=40) (actual time=0.055..0.056 rows=0 loops=1)
   Buffers: shared hit=3
   I/O Timings: read=0.000 write=0.000
   ->  Sort  (cost=3.91..3.92 rows=1 width=40) (actual time=0.053..0.054 rows=0 loops=1)
         Sort Key: organizations.id DESC
         Sort Method: quicksort  Memory: 25kB
         Buffers: shared hit=3
         I/O Timings: read=0.000 write=0.000
         ->  Nested Loop  (cost=0.13..3.90 rows=1 width=40) (actual time=0.005..0.006 rows=0 loops=1)
               I/O Timings: read=0.000 write=0.000
               ->  Seq Scan on public.organization_users  (cost=0.00..0.00 rows=1 width=8) (actual time=0.004..0.005 rows=0 loops=1)
                     Filter: (organization_users.user_id = 5413811)
                     Rows Removed by Filter: 0
                     I/O Timings: read=0.000 write=0.000
               ->  Index Scan using organizations_pkey on public.organizations  (cost=0.13..3.15 rows=1 width=40) (actual time=0.000..0.000 rows=0 loops=0)
                     Index Cond: (organizations.id = organization_users.organization_id)
                     I/O Timings: read=0.000 write=0.000

After

https://console.postgres.ai/gitlab/gitlab-production-tunnel-pg12/sessions/24341/commands/77759

Query

SELECT
    "organizations".*
FROM
    "organizations"
    INNER JOIN "organization_users" ON "organizations"."id" = "organization_users"."organization_id"
WHERE
    "organization_users"."user_id" = 5413811
    AND ("organizations"."name" ILIKE '%default%'
        OR "organizations"."path" ILIKE '%default%')
ORDER BY
    "organizations"."id" DESC
LIMIT 21

Plan

 Limit  (cost=4.13..4.13 rows=1 width=40) (actual time=1.030..1.032 rows=0 loops=1)
   Buffers: shared hit=3 read=1
   I/O Timings: read=0.895 write=0.000
   ->  Sort  (cost=4.13..4.13 rows=1 width=40) (actual time=1.028..1.029 rows=0 loops=1)
         Sort Key: organizations.id DESC
         Sort Method: quicksort  Memory: 25kB
         Buffers: shared hit=3 read=1
         I/O Timings: read=0.895 write=0.000
         ->  Nested Loop  (cost=0.00..4.12 rows=1 width=40) (actual time=0.992..0.992 rows=0 loops=1)
               Buffers: shared read=1
               I/O Timings: read=0.895 write=0.000
               ->  Seq Scan on public.organizations  (cost=0.00..4.11 rows=1 width=40) (actual time=0.973..0.984 rows=1 loops=1)
                     Filter: ((organizations.name ~~* '%default%'::text) OR (organizations.path ~~* '%default%'::text))
                     Rows Removed by Filter: 6
                     Buffers: shared read=1
                     I/O Timings: read=0.895 write=0.000
               ->  Seq Scan on public.organization_users  (cost=0.00..0.00 rows=1 width=8) (actual time=0.006..0.006 rows=0 loops=1)
                     Filter: (organization_users.user_id = 5413811)
                     Rows Removed by Filter: 0
                     I/O Timings: read=0.000 write=0.000

Screenshots or screen recordings

Screen_Recording_2023-11-21_at_3.53.09_PM

How to set up and validate locally

  1. Open the rails console
    • bin/rails console
  2. Generate some organizations and add yourself as a user (below code assumes you are signed in as root user)
you = User.find_by_username('root')
default_organization = Organizations::Organization.default_organization
Organizations::OrganizationUser.create!(organization_id: default_organization.id, user_id: you.id)

50.times do
   name = FFaker::Company.name
   organization = Organizations::Organization.create(name: name, path: name.parameterize)
   Organizations::OrganizationUser.create!(organization_id: organization.id, user_id: you.id)
end
  1. Enable the :ui_for_organizations feature flag
    • Feature.enable(:ui_for_organizations)
  2. Navigate to /-/profile/preferences and find the Home organization setting

MR acceptance checklist

This checklist encourages us to confirm any changes have been analyzed to reduce risks in quality, performance, reliability, security, and maintainability.

Edited by Peter Hegman

Merge request reports