Improve the `group#vulnerabilityGrades` GraphQL query

Why are we doing this work

The group#vulnerabilityGrades GraphQL query is responding really slow. In addition to its slowness, currently, it does not support fetching the projects for a single letter grade which makes it impossible to list all the projects for a letter grade if there are more than 100 projects in that letter grade.

Performance characteristics

Fetching the letter grade with projects
query getGrades {
  group(fullPath: "gitlab-org") {
    vulnerabilityGrades(includeSubgroups: true) {
      projects {
        pageInfo {
          endCursor
          hasNextPage
        }
        nodes {
          name
        }
      }
      grade
      count
    }
  }
}
  • Server response time: ~4500ms!
  • End-user loading time: ~5000ms(TTFB ~5000ms 🤔)
Fetching only the letter grade and the number of projects
query getGrades {
  group(fullPath: "gitlab-org") {
    vulnerabilityGrades(includeSubgroups: true) {
      grade
      count
    }
  }
}
  • Server response time: ~100ms
  • End-user loading time: ~450ms(TTFB ~450ms 🤔)

After implementing the filtering option by letter grade, we can change the frontend logic to lazy load the projects to reduce the pressure on backend;

query getGrades {
  group(fullPath: "gitlab-org") {
    vulnerabilityGrades(includeSubgroups: true, letterGrade: "F") {
      projects {
        pageInfo {
          endCursor
          hasNextPage
        }
        nodes {
          name
        }
      }
    }
  }
}

This way we can load the "Project security status" widget way faster and prevent loading unnecessary data from the server.

Implementation plan

  • backend Add filtering by letter grade option to the group#vulnerabilityGrades field.
Edited by Mehmet Emin INAC