class Gitlab::Triage::NetworkAdapters::GraphqlAdapter

Constants

Client

Public Instance Methods

query(graphql_query, resource_path: [], variables: {}) click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 14
def query(graphql_query, resource_path: [], variables: {})
  response = client.query(graphql_query, variables: variables, context: { token: options.token })

  raise_on_error!(response)

  parsed_response = parse_response(response, resource_path)
  headers = response.extensions.fetch('headers', {})

  graphql_response = {
    ratelimit_remaining: headers['ratelimit-remaining'].to_i,
    ratelimit_reset_at: Time.at(headers['ratelimit-reset'].to_i)
  }

  return graphql_response.merge(results: {}) if parsed_response.nil?
  return graphql_response.merge(results: parsed_response.map(&:to_h)) if parsed_response.is_a?(Client::List)
  return graphql_response.merge(results: parsed_response.to_h) unless parsed_response.nodes?

  graphql_response.merge(
    more_pages: parsed_response.page_info.has_next_page,
    end_cursor: parsed_response.page_info.end_cursor,
    results: parsed_response.nodes.map(&:to_h)
  )
end

Private Instance Methods

client() click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 86
def client
  @client ||= Client.new(schema: schema, execute: http_client).tap { |client| client.allow_dynamic_queries = true }
end
execute(document:, operation_name: nil, variables: {}, context: {}) click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 56
def execute(document:, operation_name: nil, variables: {}, context: {}) # rubocop:disable Lint/NestedMethodDefinition
  body = {}
  body['query'] = document.to_query_string
  body['variables'] = variables if variables.any?
  body['operationName'] = operation_name if operation_name

  response = HTTParty.post(
    uri,
    body: body.to_json,
    headers: {
      'User-Agent' => USER_AGENT,
      'Content-type' => 'application/json',
      'PRIVATE-TOKEN' => context[:token]
    }
  )

  case response.code
  when 200, 400
    JSON.parse(response.body).merge('extensions' => { 'headers' => response.headers })
  else
    { 'errors' => [{ 'message' => "#{response.code} #{response.message}" }] }
  end
end
http_client() click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 54
def http_client
  Client::HTTP.new("#{options.host_url}/api/graphql") do
    def execute(document:, operation_name: nil, variables: {}, context: {}) # rubocop:disable Lint/NestedMethodDefinition
      body = {}
      body['query'] = document.to_query_string
      body['variables'] = variables if variables.any?
      body['operationName'] = operation_name if operation_name

      response = HTTParty.post(
        uri,
        body: body.to_json,
        headers: {
          'User-Agent' => USER_AGENT,
          'Content-type' => 'application/json',
          'PRIVATE-TOKEN' => context[:token]
        }
      )

      case response.code
      when 200, 400
        JSON.parse(response.body).merge('extensions' => { 'headers' => response.headers })
      else
        { 'errors' => [{ 'message' => "#{response.code} #{response.message}" }] }
      end
    end
  end
end
parse_response(response, resource_path) click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 42
def parse_response(response, resource_path)
  resource_path.reduce(response.data) { |data, resource| data&.send(resource) }
end
raise_on_error!(response) click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 46
def raise_on_error!(response)
  return if response.errors.blank?

  puts Gitlab::Triage::UI.debug response.inspect if options.debug

  raise "There was an error: #{response.errors.messages.to_json}"
end
schema() click to toggle source
# File lib/gitlab/triage/network_adapters/graphql_adapter.rb, line 82
def schema
  @schema ||= Client.load_schema(http_client)
end