Monitor GraphQL with Prometheus
Extends graphql's platform tracing class to observe duration of graphql methods. In graphql 1.8.11 is added prometheus class but it's not very useful for us because it uses prometheus_exporter to export results.
This commit is contained in:
parent
b7b6f8483d
commit
0e66357a3e
4 changed files with 84 additions and 0 deletions
|
@ -5,6 +5,7 @@ class GitlabSchema < GraphQL::Schema
|
|||
use Gitlab::Graphql::Authorize
|
||||
use Gitlab::Graphql::Present
|
||||
use Gitlab::Graphql::Connections
|
||||
use Gitlab::Graphql::Tracing
|
||||
|
||||
query(Types::QueryType)
|
||||
|
||||
|
|
5
changelogs/unreleased/graphql-prometheus.yml
Normal file
5
changelogs/unreleased/graphql-prometheus.yml
Normal file
|
@ -0,0 +1,5 @@
|
|||
---
|
||||
title: Added prometheus monitoring to GraphQL
|
||||
merge_request:
|
||||
author:
|
||||
type: added
|
43
lib/gitlab/graphql/tracing.rb
Normal file
43
lib/gitlab/graphql/tracing.rb
Normal file
|
@ -0,0 +1,43 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
module Gitlab
|
||||
module Graphql
|
||||
class Tracing < GraphQL::Tracing::PlatformTracing
|
||||
self.platform_keys = {
|
||||
'lex' => 'graphql.lex',
|
||||
'parse' => 'graphql.parse',
|
||||
'validate' => 'graphql.validate',
|
||||
'analyze_query' => 'graphql.analyze',
|
||||
'analyze_multiplex' => 'graphql.analyze',
|
||||
'execute_multiplex' => 'graphql.execute',
|
||||
'execute_query' => 'graphql.execute',
|
||||
'execute_query_lazy' => 'graphql.execute',
|
||||
'execute_field' => 'graphql.execute',
|
||||
'execute_field_lazy' => 'graphql.execute'
|
||||
}
|
||||
|
||||
def platform_field_key(type, field)
|
||||
"#{type.name}.#{field.name}"
|
||||
end
|
||||
|
||||
def platform_trace(platform_key, key, data, &block)
|
||||
start = Gitlab::Metrics::System.monotonic_time
|
||||
|
||||
yield
|
||||
ensure
|
||||
duration = Gitlab::Metrics::System.monotonic_time - start
|
||||
|
||||
graphql_duration_seconds.observe({ platform_key: platform_key, key: key }, duration)
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def graphql_duration_seconds
|
||||
@graphql_duration_seconds ||= Gitlab::Metrics.histogram(
|
||||
:graphql_duration_seconds,
|
||||
'GraphQL execution time'
|
||||
)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
35
spec/lib/gitlab/graphql/tracing_spec.rb
Normal file
35
spec/lib/gitlab/graphql/tracing_spec.rb
Normal file
|
@ -0,0 +1,35 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
require 'spec_helper'
|
||||
|
||||
describe Gitlab::Graphql::Tracing do
|
||||
let!(:graphql_duration_seconds) { double('Gitlab::Metrics::NullMetric') }
|
||||
|
||||
before do
|
||||
allow(Gitlab::Metrics)
|
||||
.to receive(:histogram)
|
||||
.with(:graphql_duration_seconds, 'GraphQL execution time')
|
||||
.and_return(graphql_duration_seconds)
|
||||
end
|
||||
|
||||
it 'updates graphql histogram with expected labels' do
|
||||
query = 'query { users { id } }'
|
||||
|
||||
expect_metric('graphql.lex', 'lex')
|
||||
expect_metric('graphql.parse', 'parse')
|
||||
expect_metric('graphql.validate', 'validate')
|
||||
expect_metric('graphql.analyze', 'analyze_multiplex')
|
||||
expect_metric('graphql.execute', 'execute_query_lazy')
|
||||
expect_metric('graphql.execute', 'execute_multiplex')
|
||||
|
||||
GitlabSchema.execute(query)
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def expect_metric(platform_key, key)
|
||||
expect(graphql_duration_seconds)
|
||||
.to receive(:observe)
|
||||
.with({ platform_key: platform_key, key: key }, be > 0.0)
|
||||
end
|
||||
end
|
Loading…
Reference in a new issue