graphql-metrics 4.0.2 → 4.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 2af911e9031c446b604b9c296caef2c89f00cb968ecf15350a6a196d6cab08d7
4
- data.tar.gz: 94e65ae882fd6222bf3b4ed9395f32dfc395ec00c85e061a458cb5fe54b9dc67
3
+ metadata.gz: 37973ad72745f698107a0877761b9b6fd8f065da661f044eec8b59cfe8c8be0b
4
+ data.tar.gz: 06d1bc48ac6640e982ef7c258306e99b0fde8808c8f57eddf1e0ef95baceabfa
5
5
  SHA512:
6
- metadata.gz: aa3ffe4208e67594c3e65786a0a0477cdcee71506dea37988db388433eb155175d87f92e30082931e5e8c493937876e9a5a4043327b74e9e17bc474d58bd4ed9
7
- data.tar.gz: e876e9f5907cff0863a6ead3e319f34ab238b1904d0f72c8874420fdf50b5cb2941cb0f77fcfbefac35968c2bb86ec6364c5e338842dcee591eb165ee2ed14d6
6
+ metadata.gz: 25a8e51676bd6d62e9c6dd039a0b23388c7f60fbcb994ccaa171d7e1956dfb0cb0fb8d4fbb826468357bcd4cbc96a118659cde38f81f4c6303870c4b2dc7516c
7
+ data.tar.gz: a2a47c0f7a88c5f9e01e5be0bf464e3c6ff4b3a4ebf88d3c221c18e9ee6d1f65d8cf4dfe9492599d4cd386b0fa3efe33ba2887d94d2512fdcdcd6160b1743aea
@@ -1,3 +1,8 @@
1
+ 4.0.3
2
+ -----
3
+ - [32](https://github.com/Shopify/graphql-metrics/pull/32) Split validate and analyze_query tracer events (encompasses #30).
4
+ - [30](https://github.com/Shopify/graphql-metrics/pull/30) Handle queries that have already been parsed (thank you @jturkel).
5
+
1
6
  4.0.2
2
7
  -----
3
8
  - [25](https://github.com/Shopify/graphql-metrics/pull/25) Safely handle interrupted runtime metrics.
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- graphql-metrics (4.0.1)
4
+ graphql-metrics (4.0.3)
5
5
  concurrent-ruby (~> 1.1.0)
6
6
  graphql (>= 1.10.8)
7
7
 
data/README.md CHANGED
@@ -54,8 +54,8 @@ parsing and validation runtime metrics will not be added to the `metrics` hash.
54
54
  ### Define your own analyzer subclass
55
55
 
56
56
  ```ruby
57
- class CaptureAllMetricsAnalyzer < GraphQL::Metrics::Analyzer
58
- ANALYZER_NAMESPACE = :capture_all_metrics_analyzer_namespace
57
+ class SimpleAnalyzer < GraphQL::Metrics::Analyzer
58
+ ANALYZER_NAMESPACE = :simple_analyzer_namespace
59
59
 
60
60
  def initialize(query_or_multiplex)
61
61
  super
@@ -78,6 +78,8 @@ parsing and validation runtime metrics will not be added to the `metrics` hash.
78
78
  # parsing_duration: 0.0008190000080503523,
79
79
  # validation_start_time_offset: 0.0030819999519735575,
80
80
  # validation_duration: 0.01704599999357015,
81
+ # analysis_start_time_offset: 0.0010339999571442604,
82
+ # analysis_duration: 0.0008190000080503523,
81
83
  # }
82
84
  #
83
85
  # You can use these metrics to track high-level query performance, along with any other details you wish to
@@ -221,10 +223,11 @@ your application as intended, here's a breakdown of the order of execution of th
221
223
 
222
224
  When used as instrumentation, an analyzer and tracing, the order of execution is:
223
225
 
224
- * Tracer.setup_tracing_before_lexing
226
+ * Tracer.setup_tracing
225
227
  * Tracer.capture_parsing_time
226
228
  * Instrumentation.before_query (context setup)
227
- * Tracer.capture_validation_time (twice, once for `analyze_query`, then `analyze_multiplex`)
229
+ * Tracer.capture_validation_time
230
+ * Tracer.capture_analysis_time
228
231
  * Analyzer#initialize (bit more context setup, instance vars setup)
229
232
  * Analyzer#result
230
233
  * Tracer.trace_field (n times)
@@ -28,6 +28,8 @@ module GraphQL
28
28
  PARSING_DURATION = :parsing_duration
29
29
  VALIDATION_START_TIME_OFFSET = :validation_start_time_offset
30
30
  VALIDATION_DURATION = :validation_duration
31
+ ANALYSIS_START_TIME_OFFSET = :analysis_start_time_offset
32
+ ANALYSIS_DURATION = :analysis_duration
31
33
  INLINE_FIELD_TIMINGS = :inline_field_timings
32
34
  LAZY_FIELD_TIMINGS = :lazy_field_timings
33
35
 
@@ -50,7 +50,7 @@ module GraphQL
50
50
  field_name: node.name,
51
51
  return_type_name: visitor.type_definition.graphql_name,
52
52
  parent_type_name: visitor.parent_type_definition.graphql_name,
53
- deprecated: visitor.field_definition.deprecation_reason.present?,
53
+ deprecated: !visitor.field_definition.deprecation_reason.nil?,
54
54
  path: visitor.response_path,
55
55
  }
56
56
 
@@ -45,6 +45,8 @@ module GraphQL
45
45
  parsing_duration: ns[GraphQL::Metrics::PARSING_DURATION],
46
46
  validation_start_time_offset: ns[GraphQL::Metrics::VALIDATION_START_TIME_OFFSET],
47
47
  validation_duration: ns[GraphQL::Metrics::VALIDATION_DURATION],
48
+ analysis_start_time_offset: ns[GraphQL::Metrics::ANALYSIS_START_TIME_OFFSET],
49
+ analysis_duration: ns[GraphQL::Metrics::ANALYSIS_DURATION],
48
50
  }
49
51
 
50
52
  analyzer.extract_fields
@@ -4,9 +4,10 @@ module GraphQL
4
4
  module Metrics
5
5
  class Tracer
6
6
  # NOTE: These constants come from the graphql ruby gem.
7
- GRAPHQL_GEM_LEXING_KEY = 'lex'
7
+ GRAPHQL_GEM_EXECUTE_MULTIPLEX_KEY = 'execute_multiplex'
8
8
  GRAPHQL_GEM_PARSING_KEY = 'parse'
9
- GRAPHQL_GEM_VALIDATION_KEYS = ['validate', 'analyze_query']
9
+ GRAPHQL_GEM_VALIDATION_KEY = 'validate'
10
+ GRAPHQL_GEM_ANALYZE_KEY = 'analyze_query'
10
11
  GRAPHQL_GEM_TRACING_FIELD_KEYS = [
11
12
  GRAPHQL_GEM_TRACING_FIELD_KEY = 'execute_field',
12
13
  GRAPHQL_GEM_TRACING_LAZY_FIELD_KEY = 'execute_field_lazy'
@@ -22,21 +23,21 @@ module GraphQL
22
23
  # NOTE: Not all tracing events are handled here, but those that are are handled in this case statement in
23
24
  # chronological order.
24
25
  case key
25
- when GRAPHQL_GEM_LEXING_KEY
26
- return setup_tracing_before_lexing(&block)
26
+ when GRAPHQL_GEM_EXECUTE_MULTIPLEX_KEY
27
+ return setup_tracing(&block)
27
28
  when GRAPHQL_GEM_PARSING_KEY
28
29
  return capture_parsing_time(&block)
29
- when *GRAPHQL_GEM_VALIDATION_KEYS
30
+ when GRAPHQL_GEM_VALIDATION_KEY
30
31
  context = possible_context
31
-
32
- return yield unless context.query.valid?
33
32
  return capture_validation_time(context, &block)
33
+ when GRAPHQL_GEM_ANALYZE_KEY
34
+ context = possible_context
35
+ return capture_analysis_time(context, &block)
36
+
34
37
  when *GRAPHQL_GEM_TRACING_FIELD_KEYS
35
38
  return yield if data[:query].context[SKIP_FIELD_AND_ARGUMENT_METRICS]
36
39
  return yield unless GraphQL::Metrics.timings_capture_enabled?(data[:query].context)
37
40
 
38
- pre_context = nil
39
-
40
41
  context_key = case key
41
42
  when GRAPHQL_GEM_TRACING_FIELD_KEY
42
43
  GraphQL::Metrics::INLINE_FIELD_TIMINGS
@@ -52,15 +53,28 @@ module GraphQL
52
53
 
53
54
  private
54
55
 
56
+ PreContext = Struct.new(
57
+ :query_start_time,
58
+ :query_start_time_monotonic,
59
+ :parsing_start_time_offset,
60
+ :parsing_duration
61
+ ) do
62
+ def reset_parsing_timings
63
+ self[:parsing_start_time_offset] = nil
64
+ self[:parsing_duration] = nil
65
+ end
66
+ end
67
+
55
68
  def pre_context
56
69
  # NOTE: This is used to store timings from lexing, parsing, validation, before we have a context to store
57
70
  # values in. Uses thread-safe Concurrent::ThreadLocalVar to store a set of values per thread.
58
- @pre_context ||= Concurrent::ThreadLocalVar.new(OpenStruct.new)
71
+ @pre_context ||= Concurrent::ThreadLocalVar.new(PreContext.new)
72
+ @pre_context.value
59
73
  end
60
74
 
61
- def setup_tracing_before_lexing
62
- pre_context.value.query_start_time = GraphQL::Metrics.current_time
63
- pre_context.value.query_start_time_monotonic = GraphQL::Metrics.current_time_monotonic
75
+ def setup_tracing
76
+ pre_context.query_start_time = GraphQL::Metrics.current_time
77
+ pre_context.query_start_time_monotonic = GraphQL::Metrics.current_time_monotonic
64
78
 
65
79
  yield
66
80
  end
@@ -68,24 +82,41 @@ module GraphQL
68
82
  def capture_parsing_time
69
83
  timed_result = GraphQL::Metrics.time { yield }
70
84
 
71
- pre_context.value.parsing_start_time_offset = timed_result.start_time
72
- pre_context.value.parsing_duration = timed_result.duration
85
+ pre_context.parsing_start_time_offset = timed_result.start_time
86
+ pre_context.parsing_duration = timed_result.duration
73
87
 
74
88
  timed_result.result
75
89
  end
76
90
 
77
91
  def capture_validation_time(context)
78
- timed_result = GraphQL::Metrics.time(pre_context.value.query_start_time_monotonic) { yield }
92
+ if pre_context.parsing_duration.nil?
93
+ pre_context.parsing_start_time_offset = 0
94
+ pre_context.parsing_duration = 0
95
+ end
96
+
97
+ timed_result = GraphQL::Metrics.time(pre_context.query_start_time_monotonic) { yield }
79
98
 
80
99
  ns = context.namespace(CONTEXT_NAMESPACE)
81
- previous_validation_duration = ns[GraphQL::Metrics::VALIDATION_DURATION] || 0
82
100
 
83
- ns[QUERY_START_TIME] = pre_context.value.query_start_time
84
- ns[QUERY_START_TIME_MONOTONIC] = pre_context.value.query_start_time_monotonic
85
- ns[PARSING_START_TIME_OFFSET] = pre_context.value.parsing_start_time_offset
86
- ns[PARSING_DURATION] = pre_context.value.parsing_duration
101
+ ns[QUERY_START_TIME] = pre_context.query_start_time
102
+ ns[QUERY_START_TIME_MONOTONIC] = pre_context.query_start_time_monotonic
103
+ ns[PARSING_START_TIME_OFFSET] = pre_context.parsing_start_time_offset
104
+ ns[PARSING_DURATION] = pre_context.parsing_duration
87
105
  ns[VALIDATION_START_TIME_OFFSET] = timed_result.time_since_offset
88
- ns[VALIDATION_DURATION] = timed_result.duration + previous_validation_duration
106
+ ns[VALIDATION_DURATION] = timed_result.duration
107
+
108
+ pre_context.reset_parsing_timings
109
+
110
+ timed_result.result
111
+ end
112
+
113
+ def capture_analysis_time(context)
114
+ ns = context.namespace(CONTEXT_NAMESPACE)
115
+
116
+ timed_result = GraphQL::Metrics.time(ns[QUERY_START_TIME_MONOTONIC]) { yield }
117
+
118
+ ns[ANALYSIS_START_TIME_OFFSET] = timed_result.time_since_offset
119
+ ns[ANALYSIS_DURATION] = timed_result.duration
89
120
 
90
121
  timed_result.result
91
122
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module GraphQL
4
4
  module Metrics
5
- VERSION = "4.0.2"
5
+ VERSION = "4.0.3"
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: graphql-metrics
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.0.2
4
+ version: 4.0.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Christopher Butcher
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-06-11 00:00:00.000000000 Z
11
+ date: 2020-08-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: graphql