graphql 2.0.32 → 2.5.22

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.
Files changed (308) hide show
  1. checksums.yaml +4 -4
  2. data/lib/generators/graphql/detailed_trace_generator.rb +77 -0
  3. data/lib/generators/graphql/install/mutation_root_generator.rb +2 -2
  4. data/lib/generators/graphql/install/templates/base_mutation.erb +2 -0
  5. data/lib/generators/graphql/install/templates/mutation_type.erb +2 -0
  6. data/lib/generators/graphql/install_generator.rb +49 -0
  7. data/lib/generators/graphql/orm_mutations_base.rb +1 -1
  8. data/lib/generators/graphql/templates/base_argument.erb +2 -0
  9. data/lib/generators/graphql/templates/base_connection.erb +2 -0
  10. data/lib/generators/graphql/templates/base_edge.erb +2 -0
  11. data/lib/generators/graphql/templates/base_enum.erb +2 -0
  12. data/lib/generators/graphql/templates/base_field.erb +2 -0
  13. data/lib/generators/graphql/templates/base_input_object.erb +2 -0
  14. data/lib/generators/graphql/templates/base_interface.erb +2 -0
  15. data/lib/generators/graphql/templates/base_object.erb +2 -0
  16. data/lib/generators/graphql/templates/base_resolver.erb +8 -0
  17. data/lib/generators/graphql/templates/base_scalar.erb +2 -0
  18. data/lib/generators/graphql/templates/base_union.erb +2 -0
  19. data/lib/generators/graphql/templates/create_graphql_detailed_traces.erb +10 -0
  20. data/lib/generators/graphql/templates/graphql_controller.erb +2 -0
  21. data/lib/generators/graphql/templates/loader.erb +2 -0
  22. data/lib/generators/graphql/templates/mutation.erb +2 -0
  23. data/lib/generators/graphql/templates/node_type.erb +2 -0
  24. data/lib/generators/graphql/templates/query_type.erb +2 -0
  25. data/lib/generators/graphql/templates/schema.erb +5 -0
  26. data/lib/generators/graphql/type_generator.rb +1 -1
  27. data/lib/graphql/analysis/analyzer.rb +90 -0
  28. data/lib/graphql/analysis/field_usage.rb +82 -0
  29. data/lib/graphql/analysis/max_query_complexity.rb +20 -0
  30. data/lib/graphql/analysis/max_query_depth.rb +20 -0
  31. data/lib/graphql/analysis/query_complexity.rb +263 -0
  32. data/lib/graphql/analysis/query_depth.rb +58 -0
  33. data/lib/graphql/analysis/visitor.rb +280 -0
  34. data/lib/graphql/analysis.rb +95 -1
  35. data/lib/graphql/autoload.rb +38 -0
  36. data/lib/graphql/backtrace/table.rb +118 -55
  37. data/lib/graphql/backtrace.rb +1 -19
  38. data/lib/graphql/coercion_error.rb +1 -9
  39. data/lib/graphql/current.rb +57 -0
  40. data/lib/graphql/dashboard/application_controller.rb +41 -0
  41. data/lib/graphql/dashboard/detailed_traces.rb +47 -0
  42. data/lib/graphql/dashboard/installable.rb +22 -0
  43. data/lib/graphql/dashboard/landings_controller.rb +9 -0
  44. data/lib/graphql/dashboard/limiters.rb +93 -0
  45. data/lib/graphql/dashboard/operation_store.rb +199 -0
  46. data/lib/graphql/dashboard/statics/bootstrap-5.3.3.min.css +6 -0
  47. data/lib/graphql/dashboard/statics/bootstrap-5.3.3.min.js +7 -0
  48. data/lib/graphql/dashboard/statics/charts.min.css +1 -0
  49. data/lib/graphql/dashboard/statics/dashboard.css +30 -0
  50. data/lib/graphql/dashboard/statics/dashboard.js +143 -0
  51. data/lib/graphql/dashboard/statics/header-icon.png +0 -0
  52. data/lib/graphql/dashboard/statics/icon.png +0 -0
  53. data/lib/graphql/dashboard/statics_controller.rb +31 -0
  54. data/lib/graphql/dashboard/subscriptions.rb +97 -0
  55. data/lib/graphql/dashboard/views/graphql/dashboard/detailed_traces/traces/index.html.erb +45 -0
  56. data/lib/graphql/dashboard/views/graphql/dashboard/landings/show.html.erb +18 -0
  57. data/lib/graphql/dashboard/views/graphql/dashboard/limiters/limiters/show.html.erb +62 -0
  58. data/lib/graphql/dashboard/views/graphql/dashboard/not_installed.html.erb +18 -0
  59. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/_form.html.erb +24 -0
  60. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/edit.html.erb +21 -0
  61. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/index.html.erb +69 -0
  62. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/new.html.erb +7 -0
  63. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/index_entries/index.html.erb +39 -0
  64. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/index_entries/show.html.erb +32 -0
  65. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/operations/index.html.erb +81 -0
  66. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/operations/show.html.erb +71 -0
  67. data/lib/graphql/dashboard/views/graphql/dashboard/subscriptions/subscriptions/show.html.erb +41 -0
  68. data/lib/graphql/dashboard/views/graphql/dashboard/subscriptions/topics/index.html.erb +55 -0
  69. data/lib/graphql/dashboard/views/graphql/dashboard/subscriptions/topics/show.html.erb +40 -0
  70. data/lib/graphql/dashboard/views/layouts/graphql/dashboard/application.html.erb +108 -0
  71. data/lib/graphql/dashboard.rb +96 -0
  72. data/lib/graphql/dataloader/active_record_association_source.rb +84 -0
  73. data/lib/graphql/dataloader/active_record_source.rb +47 -0
  74. data/lib/graphql/dataloader/async_dataloader.rb +112 -0
  75. data/lib/graphql/dataloader/null_dataloader.rb +55 -10
  76. data/lib/graphql/dataloader/request.rb +5 -0
  77. data/lib/graphql/dataloader/source.rb +35 -12
  78. data/lib/graphql/dataloader.rb +224 -149
  79. data/lib/graphql/date_encoding_error.rb +1 -1
  80. data/lib/graphql/dig.rb +2 -1
  81. data/lib/graphql/duration_encoding_error.rb +16 -0
  82. data/lib/graphql/execution/interpreter/argument_value.rb +5 -1
  83. data/lib/graphql/execution/interpreter/arguments_cache.rb +5 -10
  84. data/lib/graphql/execution/interpreter/resolve.rb +23 -25
  85. data/lib/graphql/execution/interpreter/runtime/graphql_result.rb +228 -0
  86. data/lib/graphql/execution/interpreter/runtime.rb +363 -434
  87. data/lib/graphql/execution/interpreter.rb +91 -164
  88. data/lib/graphql/execution/lookahead.rb +105 -31
  89. data/lib/graphql/execution/multiplex.rb +7 -6
  90. data/lib/graphql/execution/next/field_resolve_step.rb +711 -0
  91. data/lib/graphql/execution/next/load_argument_step.rb +60 -0
  92. data/lib/graphql/execution/next/prepare_object_step.rb +129 -0
  93. data/lib/graphql/execution/next/runner.rb +389 -0
  94. data/lib/graphql/execution/next/selections_step.rb +37 -0
  95. data/lib/graphql/execution/next.rb +70 -0
  96. data/lib/graphql/execution.rb +1 -0
  97. data/lib/graphql/execution_error.rb +13 -10
  98. data/lib/graphql/introspection/directive_location_enum.rb +1 -1
  99. data/lib/graphql/introspection/directive_type.rb +7 -3
  100. data/lib/graphql/introspection/dynamic_fields.rb +5 -1
  101. data/lib/graphql/introspection/entry_points.rb +20 -6
  102. data/lib/graphql/introspection/enum_value_type.rb +5 -5
  103. data/lib/graphql/introspection/field_type.rb +13 -5
  104. data/lib/graphql/introspection/input_value_type.rb +21 -13
  105. data/lib/graphql/introspection/schema_type.rb +8 -11
  106. data/lib/graphql/introspection/type_type.rb +64 -28
  107. data/lib/graphql/invalid_name_error.rb +1 -1
  108. data/lib/graphql/invalid_null_error.rb +26 -17
  109. data/lib/graphql/language/block_string.rb +34 -18
  110. data/lib/graphql/language/cache.rb +13 -0
  111. data/lib/graphql/language/comment.rb +18 -0
  112. data/lib/graphql/language/definition_slice.rb +1 -1
  113. data/lib/graphql/language/document_from_schema_definition.rb +90 -61
  114. data/lib/graphql/language/lexer.rb +319 -193
  115. data/lib/graphql/language/nodes.rb +136 -77
  116. data/lib/graphql/language/parser.rb +807 -1985
  117. data/lib/graphql/language/printer.rb +324 -151
  118. data/lib/graphql/language/sanitized_printer.rb +21 -23
  119. data/lib/graphql/language/static_visitor.rb +171 -0
  120. data/lib/graphql/language/visitor.rb +23 -83
  121. data/lib/graphql/language.rb +71 -1
  122. data/lib/graphql/load_application_object_failed_error.rb +5 -1
  123. data/lib/graphql/pagination/array_connection.rb +6 -6
  124. data/lib/graphql/pagination/connection.rb +30 -1
  125. data/lib/graphql/pagination/connections.rb +32 -0
  126. data/lib/graphql/pagination/mongoid_relation_connection.rb +1 -2
  127. data/lib/graphql/query/context/scoped_context.rb +101 -0
  128. data/lib/graphql/query/context.rb +82 -144
  129. data/lib/graphql/query/null_context.rb +15 -18
  130. data/lib/graphql/query/partial.rb +179 -0
  131. data/lib/graphql/query/validation_pipeline.rb +4 -4
  132. data/lib/graphql/query/variable_validation_error.rb +1 -1
  133. data/lib/graphql/query/variables.rb +3 -3
  134. data/lib/graphql/query.rb +126 -81
  135. data/lib/graphql/railtie.rb +16 -6
  136. data/lib/graphql/rake_task.rb +3 -12
  137. data/lib/graphql/rubocop/graphql/base_cop.rb +1 -1
  138. data/lib/graphql/rubocop/graphql/field_type_in_block.rb +144 -0
  139. data/lib/graphql/rubocop/graphql/root_types_in_block.rb +38 -0
  140. data/lib/graphql/rubocop.rb +2 -0
  141. data/lib/graphql/schema/addition.rb +26 -13
  142. data/lib/graphql/schema/always_visible.rb +7 -2
  143. data/lib/graphql/schema/argument.rb +75 -9
  144. data/lib/graphql/schema/base_64_encoder.rb +3 -5
  145. data/lib/graphql/schema/build_from_definition.rb +123 -60
  146. data/lib/graphql/schema/directive/flagged.rb +4 -2
  147. data/lib/graphql/schema/directive/one_of.rb +12 -0
  148. data/lib/graphql/schema/directive/specified_by.rb +14 -0
  149. data/lib/graphql/schema/directive.rb +54 -2
  150. data/lib/graphql/schema/enum.rb +110 -27
  151. data/lib/graphql/schema/enum_value.rb +10 -2
  152. data/lib/graphql/schema/field/connection_extension.rb +15 -49
  153. data/lib/graphql/schema/field/scope_extension.rb +23 -7
  154. data/lib/graphql/schema/field.rb +245 -118
  155. data/lib/graphql/schema/field_extension.rb +34 -1
  156. data/lib/graphql/schema/has_single_input_argument.rb +160 -0
  157. data/lib/graphql/schema/input_object.rb +116 -60
  158. data/lib/graphql/schema/interface.rb +34 -16
  159. data/lib/graphql/schema/introspection_system.rb +8 -17
  160. data/lib/graphql/schema/late_bound_type.rb +4 -0
  161. data/lib/graphql/schema/list.rb +3 -3
  162. data/lib/graphql/schema/loader.rb +3 -4
  163. data/lib/graphql/schema/member/base_dsl_methods.rb +18 -2
  164. data/lib/graphql/schema/member/has_arguments.rb +132 -100
  165. data/lib/graphql/schema/member/has_authorization.rb +35 -0
  166. data/lib/graphql/schema/member/has_dataloader.rb +99 -0
  167. data/lib/graphql/schema/member/has_deprecation_reason.rb +15 -0
  168. data/lib/graphql/schema/member/has_directives.rb +4 -4
  169. data/lib/graphql/schema/member/has_fields.rb +115 -15
  170. data/lib/graphql/schema/member/has_interfaces.rb +26 -12
  171. data/lib/graphql/schema/member/has_unresolved_type_error.rb +5 -1
  172. data/lib/graphql/schema/member/has_validators.rb +1 -1
  173. data/lib/graphql/schema/member/relay_shortcuts.rb +1 -1
  174. data/lib/graphql/schema/member/scoped.rb +19 -0
  175. data/lib/graphql/schema/member/type_system_helpers.rb +17 -4
  176. data/lib/graphql/schema/member/validates_input.rb +3 -3
  177. data/lib/graphql/schema/member.rb +6 -0
  178. data/lib/graphql/schema/mutation.rb +7 -0
  179. data/lib/graphql/schema/object.rb +34 -8
  180. data/lib/graphql/schema/printer.rb +9 -7
  181. data/lib/graphql/schema/ractor_shareable.rb +79 -0
  182. data/lib/graphql/schema/relay_classic_mutation.rb +6 -129
  183. data/lib/graphql/schema/resolver.rb +90 -32
  184. data/lib/graphql/schema/scalar.rb +4 -9
  185. data/lib/graphql/schema/subscription.rb +63 -10
  186. data/lib/graphql/schema/timeout.rb +19 -2
  187. data/lib/graphql/schema/type_expression.rb +2 -2
  188. data/lib/graphql/schema/union.rb +2 -2
  189. data/lib/graphql/schema/unique_within_type.rb +1 -1
  190. data/lib/graphql/schema/validator/all_validator.rb +62 -0
  191. data/lib/graphql/schema/validator/required_validator.rb +92 -11
  192. data/lib/graphql/schema/validator.rb +3 -1
  193. data/lib/graphql/schema/visibility/migration.rb +188 -0
  194. data/lib/graphql/schema/visibility/profile.rb +445 -0
  195. data/lib/graphql/schema/visibility/visit.rb +190 -0
  196. data/lib/graphql/schema/visibility.rb +311 -0
  197. data/lib/graphql/schema/warden.rb +275 -103
  198. data/lib/graphql/schema.rb +950 -210
  199. data/lib/graphql/static_validation/all_rules.rb +3 -3
  200. data/lib/graphql/static_validation/base_visitor.rb +7 -6
  201. data/lib/graphql/static_validation/literal_validator.rb +6 -7
  202. data/lib/graphql/static_validation/rules/argument_literals_are_compatible.rb +1 -1
  203. data/lib/graphql/static_validation/rules/argument_names_are_unique.rb +1 -1
  204. data/lib/graphql/static_validation/rules/arguments_are_defined.rb +3 -2
  205. data/lib/graphql/static_validation/rules/directives_are_defined.rb +3 -3
  206. data/lib/graphql/static_validation/rules/directives_are_in_valid_locations.rb +2 -0
  207. data/lib/graphql/static_validation/rules/fields_are_defined_on_type.rb +12 -2
  208. data/lib/graphql/static_validation/rules/fields_have_appropriate_selections.rb +47 -13
  209. data/lib/graphql/static_validation/rules/fields_will_merge.rb +88 -25
  210. data/lib/graphql/static_validation/rules/fields_will_merge_error.rb +10 -2
  211. data/lib/graphql/static_validation/rules/fragment_spreads_are_possible.rb +3 -3
  212. data/lib/graphql/static_validation/rules/fragment_types_exist.rb +12 -2
  213. data/lib/graphql/static_validation/rules/fragments_are_on_composite_types.rb +1 -1
  214. data/lib/graphql/static_validation/rules/mutation_root_exists.rb +1 -1
  215. data/lib/graphql/static_validation/rules/no_definitions_are_present.rb +1 -1
  216. data/lib/graphql/static_validation/rules/not_single_subscription_error.rb +25 -0
  217. data/lib/graphql/static_validation/rules/query_root_exists.rb +1 -1
  218. data/lib/graphql/static_validation/rules/required_arguments_are_present.rb +5 -5
  219. data/lib/graphql/static_validation/rules/required_input_object_attributes_are_present.rb +5 -5
  220. data/lib/graphql/static_validation/rules/subscription_root_exists_and_single_subscription_selection.rb +26 -0
  221. data/lib/graphql/static_validation/rules/unique_directives_per_location.rb +7 -3
  222. data/lib/graphql/static_validation/rules/variable_default_values_are_correctly_typed.rb +18 -27
  223. data/lib/graphql/static_validation/rules/variable_names_are_unique.rb +1 -1
  224. data/lib/graphql/static_validation/rules/variable_usages_are_allowed.rb +2 -2
  225. data/lib/graphql/static_validation/rules/variables_are_input_types.rb +11 -2
  226. data/lib/graphql/static_validation/validation_context.rb +21 -5
  227. data/lib/graphql/static_validation/validator.rb +9 -1
  228. data/lib/graphql/static_validation.rb +0 -1
  229. data/lib/graphql/subscriptions/action_cable_subscriptions.rb +8 -5
  230. data/lib/graphql/subscriptions/broadcast_analyzer.rb +11 -5
  231. data/lib/graphql/subscriptions/default_subscription_resolve_extension.rb +12 -10
  232. data/lib/graphql/subscriptions/event.rb +21 -4
  233. data/lib/graphql/subscriptions/serialize.rb +3 -1
  234. data/lib/graphql/subscriptions.rb +21 -17
  235. data/lib/graphql/testing/helpers.rb +161 -0
  236. data/lib/graphql/testing/mock_action_cable.rb +111 -0
  237. data/lib/graphql/testing.rb +3 -0
  238. data/lib/graphql/tracing/active_support_notifications_trace.rb +14 -3
  239. data/lib/graphql/tracing/active_support_notifications_tracing.rb +1 -1
  240. data/lib/graphql/tracing/appoptics_trace.rb +7 -3
  241. data/lib/graphql/tracing/appoptics_tracing.rb +9 -2
  242. data/lib/graphql/tracing/appsignal_trace.rb +32 -59
  243. data/lib/graphql/tracing/appsignal_tracing.rb +2 -0
  244. data/lib/graphql/tracing/call_legacy_tracers.rb +66 -0
  245. data/lib/graphql/tracing/data_dog_trace.rb +46 -162
  246. data/lib/graphql/tracing/data_dog_tracing.rb +2 -0
  247. data/lib/graphql/tracing/detailed_trace/active_record_backend.rb +74 -0
  248. data/lib/graphql/tracing/detailed_trace/memory_backend.rb +60 -0
  249. data/lib/graphql/tracing/detailed_trace/redis_backend.rb +72 -0
  250. data/lib/graphql/tracing/detailed_trace.rb +156 -0
  251. data/lib/graphql/tracing/legacy_hooks_trace.rb +75 -0
  252. data/lib/graphql/tracing/legacy_trace.rb +4 -61
  253. data/lib/graphql/tracing/monitor_trace.rb +283 -0
  254. data/lib/graphql/tracing/new_relic_trace.rb +47 -54
  255. data/lib/graphql/tracing/new_relic_tracing.rb +2 -0
  256. data/lib/graphql/tracing/notifications_trace.rb +183 -37
  257. data/lib/graphql/tracing/notifications_tracing.rb +2 -0
  258. data/lib/graphql/tracing/null_trace.rb +9 -0
  259. data/lib/graphql/tracing/perfetto_trace/trace.proto +141 -0
  260. data/lib/graphql/tracing/perfetto_trace/trace_pb.rb +33 -0
  261. data/lib/graphql/tracing/perfetto_trace.rb +864 -0
  262. data/lib/graphql/tracing/platform_tracing.rb +3 -1
  263. data/lib/graphql/tracing/{prometheus_tracing → prometheus_trace}/graphql_collector.rb +5 -1
  264. data/lib/graphql/tracing/prometheus_trace.rb +73 -73
  265. data/lib/graphql/tracing/prometheus_tracing.rb +2 -0
  266. data/lib/graphql/tracing/scout_trace.rb +32 -58
  267. data/lib/graphql/tracing/scout_tracing.rb +2 -0
  268. data/lib/graphql/tracing/sentry_trace.rb +82 -0
  269. data/lib/graphql/tracing/statsd_trace.rb +33 -45
  270. data/lib/graphql/tracing/statsd_tracing.rb +2 -0
  271. data/lib/graphql/tracing/trace.rb +112 -1
  272. data/lib/graphql/tracing.rb +31 -28
  273. data/lib/graphql/type_kinds.rb +2 -1
  274. data/lib/graphql/types/iso_8601_duration.rb +77 -0
  275. data/lib/graphql/types/relay/connection_behaviors.rb +44 -2
  276. data/lib/graphql/types/relay/edge_behaviors.rb +18 -0
  277. data/lib/graphql/types/relay/has_node_field.rb +13 -8
  278. data/lib/graphql/types/relay/has_nodes_field.rb +13 -8
  279. data/lib/graphql/types/relay/node_behaviors.rb +13 -2
  280. data/lib/graphql/types/relay/page_info_behaviors.rb +4 -0
  281. data/lib/graphql/types.rb +18 -10
  282. data/lib/graphql/unauthorized_enum_value_error.rb +13 -0
  283. data/lib/graphql/unauthorized_error.rb +5 -1
  284. data/lib/graphql/version.rb +1 -1
  285. data/lib/graphql.rb +71 -54
  286. data/readme.md +12 -2
  287. metadata +233 -37
  288. data/lib/graphql/analysis/ast/analyzer.rb +0 -84
  289. data/lib/graphql/analysis/ast/field_usage.rb +0 -57
  290. data/lib/graphql/analysis/ast/max_query_complexity.rb +0 -22
  291. data/lib/graphql/analysis/ast/max_query_depth.rb +0 -22
  292. data/lib/graphql/analysis/ast/query_complexity.rb +0 -230
  293. data/lib/graphql/analysis/ast/query_depth.rb +0 -55
  294. data/lib/graphql/analysis/ast/visitor.rb +0 -276
  295. data/lib/graphql/analysis/ast.rb +0 -81
  296. data/lib/graphql/backtrace/inspect_result.rb +0 -50
  297. data/lib/graphql/backtrace/trace.rb +0 -96
  298. data/lib/graphql/backtrace/tracer.rb +0 -80
  299. data/lib/graphql/deprecation.rb +0 -9
  300. data/lib/graphql/filter.rb +0 -59
  301. data/lib/graphql/language/parser.y +0 -560
  302. data/lib/graphql/language/token.rb +0 -34
  303. data/lib/graphql/schema/base_64_bp.rb +0 -26
  304. data/lib/graphql/schema/invalid_type_error.rb +0 -7
  305. data/lib/graphql/schema/null_mask.rb +0 -11
  306. data/lib/graphql/static_validation/rules/subscription_root_exists.rb +0 -17
  307. data/lib/graphql/static_validation/type_stack.rb +0 -216
  308. data/lib/graphql/subscriptions/instrumentation.rb +0 -28
@@ -81,10 +81,12 @@ module GraphQL
81
81
  trace_name = tracing_name.sub("Tracing", "Trace")
82
82
  if GraphQL::Tracing.const_defined?(trace_name, false)
83
83
  trace_module = GraphQL::Tracing.const_get(trace_name)
84
+ warn("`use(#{self.name})` is deprecated, use the equivalent `trace_with(#{trace_module.name})` instead. More info: https://graphql-ruby.org/queries/tracing.html")
84
85
  schema_defn.trace_with(trace_module, **options)
85
86
  else
87
+ warn("`use(#{self.name})` and `Tracing::PlatformTracing` are deprecated. Use a `trace_with(...)` module instead. More info: https://graphql-ruby.org/queries/tracing.html. Please open an issue on the GraphQL-Ruby repo if you want to discuss further!")
86
88
  tracer = self.new(**options)
87
- schema_defn.tracer(tracer)
89
+ schema_defn.tracer(tracer, silence_deprecation_warning: true)
88
90
  end
89
91
  end
90
92
  end
@@ -1,8 +1,10 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing"
4
+
3
5
  module GraphQL
4
6
  module Tracing
5
- class PrometheusTracing < PlatformTracing
7
+ module PrometheusTrace
6
8
  class GraphQLCollector < ::PrometheusExporter::Server::TypeCollector
7
9
  def initialize
8
10
  @graphql_gauge = PrometheusExporter::Metric::Base.default_aggregation.new(
@@ -28,5 +30,7 @@ module GraphQL
28
30
  end
29
31
  end
30
32
  end
33
+ # Backwards-compat:
34
+ PrometheusTracing::GraphQLCollector = PrometheusTrace::GraphQLCollector
31
35
  end
32
36
  end
@@ -1,91 +1,91 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/monitor_trace"
4
+
3
5
  module GraphQL
4
6
  module Tracing
7
+ # A tracer for reporting GraphQL-Ruby times to Prometheus.
8
+ #
9
+ # The PrometheusExporter server must be run with a custom type collector that extends `GraphQL::Tracing::PrometheusTracing::GraphQLCollector`.
10
+ #
11
+ # @example Adding this trace to your schema
12
+ # require 'prometheus_exporter/client'
13
+ #
14
+ # class MySchema < GraphQL::Schema
15
+ # trace_with GraphQL::Tracing::PrometheusTrace
16
+ # end
17
+ #
18
+ # @example Running a custom type collector
19
+ # # lib/graphql_collector.rb
20
+ # if defined?(PrometheusExporter::Server)
21
+ # require 'graphql/tracing'
22
+ #
23
+ # class GraphQLCollector < GraphQL::Tracing::PrometheusTrace::GraphQLCollector
24
+ # end
25
+ # end
26
+ #
27
+ # # Then run:
28
+ # # bundle exec prometheus_exporter -a lib/graphql_collector.rb
29
+ PrometheusTrace = MonitorTrace.create_module("prometheus")
5
30
  module PrometheusTrace
6
- include PlatformTrace
7
-
8
- def initialize(client: PrometheusExporter::Client.default, keys_whitelist: ["execute_field", "execute_field_lazy"], collector_type: "graphql", **rest)
9
- @client = client
10
- @keys_whitelist = keys_whitelist
11
- @collector_type = collector_type
12
-
13
- super(**rest)
14
- end
15
-
16
- # rubocop:disable Development/NoEvalCop This eval takes static inputs at load-time
17
-
18
- {
19
- 'lex' => "graphql.lex",
20
- 'parse' => "graphql.parse",
21
- 'validate' => "graphql.validate",
22
- 'analyze_query' => "graphql.analyze",
23
- 'analyze_multiplex' => "graphql.analyze",
24
- 'execute_multiplex' => "graphql.execute",
25
- 'execute_query' => "graphql.execute",
26
- 'execute_query_lazy' => "graphql.execute",
27
- }.each do |trace_method, platform_key|
28
- module_eval <<-RUBY, __FILE__, __LINE__
29
- def #{trace_method}(**data, &block)
30
- instrument_execution("#{platform_key}", "#{trace_method}", &block)
31
- end
32
- RUBY
31
+ if defined?(PrometheusExporter::Server)
32
+ autoload :GraphQLCollector, "graphql/tracing/prometheus_trace/graphql_collector"
33
33
  end
34
34
 
35
- # rubocop:enable Development/NoEvalCop
36
-
37
- def platform_execute_field(platform_key, &block)
38
- instrument_execution(platform_key, "execute_field", &block)
35
+ def initialize(client: PrometheusExporter::Client.default, keys_whitelist: [:execute_field], collector_type: "graphql", **rest)
36
+ @prometheus_client = client
37
+ @prometheus_keys_whitelist = keys_whitelist.map(&:to_sym) # handle previous string keys
38
+ @prometheus_collector_type = collector_type
39
+ setup_prometheus_monitor(**rest)
40
+ super
39
41
  end
40
42
 
41
- def platform_execute_field_lazy(platform_key, &block)
42
- instrument_execution(platform_key, "execute_field_lazy", &block)
43
- end
44
-
45
- def platform_authorized(platform_key, &block)
46
- instrument_execution(platform_key, "authorized", &block)
47
- end
48
-
49
- def platform_authorized_lazy(platform_key, &block)
50
- instrument_execution(platform_key, "authorized_lazy", &block)
51
- end
52
-
53
- def platform_resolve_type(platform_key, &block)
54
- instrument_execution(platform_key, "resolve_type", &block)
55
- end
43
+ attr_reader :prometheus_collector_type, :prometheus_client, :prometheus_keys_whitelist
44
+
45
+ class PrometheusMonitor < MonitorTrace::Monitor
46
+ def instrument(keyword, object)
47
+ if active?(keyword)
48
+ start = gettime
49
+ result = yield
50
+ duration = gettime - start
51
+ send_json(duration, keyword, object)
52
+ result
53
+ else
54
+ yield
55
+ end
56
+ end
56
57
 
57
- def platform_resolve_type_lazy(platform_key, &block)
58
- instrument_execution(platform_key, "resolve_type_lazy", &block)
59
- end
58
+ def active?(keyword)
59
+ @trace.prometheus_keys_whitelist.include?(keyword)
60
+ end
60
61
 
61
- def platform_field_key(field)
62
- field.path
63
- end
62
+ def gettime
63
+ ::Process.clock_gettime(::Process::CLOCK_MONOTONIC)
64
+ end
64
65
 
65
- def platform_authorized_key(type)
66
- "#{type.graphql_name}.authorized"
67
- end
66
+ def send_json(duration, keyword, object)
67
+ event_name = name_for(keyword, object)
68
+ @trace.prometheus_client.send_json(
69
+ type: @trace.prometheus_collector_type,
70
+ duration: duration,
71
+ platform_key: event_name,
72
+ key: keyword
73
+ )
74
+ end
68
75
 
69
- def platform_resolve_type_key(type)
70
- "#{type.graphql_name}.resolve_type"
71
- end
76
+ include MonitorTrace::Monitor::GraphQLPrefixNames
72
77
 
73
- private
78
+ class Event < MonitorTrace::Monitor::Event
79
+ def start
80
+ @start_time = @monitor.gettime
81
+ end
74
82
 
75
- def instrument_execution(platform_key, key, &block)
76
- if @keys_whitelist.include?(key)
77
- start = ::Process.clock_gettime ::Process::CLOCK_MONOTONIC
78
- result = block.call
79
- duration = ::Process.clock_gettime(::Process::CLOCK_MONOTONIC) - start
80
- @client.send_json(
81
- type: @collector_type,
82
- duration: duration,
83
- platform_key: platform_key,
84
- key: key
85
- )
86
- result
87
- else
88
- yield
83
+ def finish
84
+ if @monitor.active?(keyword)
85
+ duration = @monitor.gettime - @start_time
86
+ @monitor.send_json(duration, keyword, object)
87
+ end
88
+ end
89
89
  end
90
90
  end
91
91
  end
@@ -1,5 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/platform_tracing"
4
+
3
5
  module GraphQL
4
6
  module Tracing
5
7
  class PrometheusTracing < PlatformTracing
@@ -1,74 +1,48 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/monitor_trace"
4
+
3
5
  module GraphQL
4
6
  module Tracing
7
+ # A tracer for sending GraphQL-Ruby times to Scout
8
+ #
9
+ # @example Adding this tracer to your schema
10
+ # class MySchema < GraphQL::Schema
11
+ # trace_with GraphQL::Tracing::ScoutTrace
12
+ # end
13
+ ScoutTrace = MonitorTrace.create_module("scout")
5
14
  module ScoutTrace
6
- include PlatformTrace
7
-
8
- INSTRUMENT_OPTS = { scope: true }
9
-
10
- # @param set_transaction_name [Boolean] If true, the GraphQL operation name will be used as the transaction name.
11
- # This is not advised if you run more than one query per HTTP request, for example, with `graphql-client` or multiplexing.
12
- # It can also be specified per-query with `context[:set_scout_transaction_name]`.
13
- def initialize(set_transaction_name: false, **_rest)
14
- self.class.include(ScoutApm::Tracer)
15
- @set_transaction_name = set_transaction_name
16
- super
17
- end
18
-
19
- # rubocop:disable Development/NoEvalCop This eval takes static inputs at load-time
20
-
21
- {
22
- "lex" => "lex.graphql",
23
- "parse" => "parse.graphql",
24
- "validate" => "validate.graphql",
25
- "analyze_query" => "analyze.graphql",
26
- "analyze_multiplex" => "analyze.graphql",
27
- "execute_multiplex" => "execute.graphql",
28
- "execute_query" => "execute.graphql",
29
- "execute_query_lazy" => "execute.graphql",
30
- }.each do |trace_method, platform_key|
31
- module_eval <<-RUBY, __FILE__, __LINE__
32
- def #{trace_method}(**data)
33
- #{
34
- if trace_method == "execute_query"
35
- <<-RUBY
36
- set_this_txn_name = data[:query].context[:set_scout_transaction_name]
37
- if set_this_txn_name == true || (set_this_txn_name.nil? && @set_transaction_name)
38
- ScoutApm::Transaction.rename(transaction_name(data[:query]))
39
- end
40
- RUBY
15
+ class ScoutMonitor < MonitorTrace::Monitor
16
+ def instrument(keyword, object)
17
+ if keyword == :execute
18
+ query = object.queries.first
19
+ set_this_txn_name = query.context[:set_scout_transaction_name]
20
+ if set_this_txn_name == true || (set_this_txn_name.nil? && @set_transaction_name)
21
+ ScoutApm::Transaction.rename(transaction_name(query))
41
22
  end
42
- }
23
+ end
43
24
 
44
- self.class.instrument("GraphQL", "#{platform_key}", INSTRUMENT_OPTS) do
45
- super
25
+ ScoutApm::Tracer.instrument("GraphQL", name_for(keyword, object), INSTRUMENT_OPTS) do
26
+ yield
46
27
  end
47
28
  end
48
- RUBY
49
- end
50
- # rubocop:enable Development/NoEvalCop
51
29
 
52
- def platform_execute_field(platform_key, &block)
53
- self.class.instrument("GraphQL", platform_key, INSTRUMENT_OPTS, &block)
54
- end
30
+ INSTRUMENT_OPTS = { scope: true }
55
31
 
56
- def platform_authorized(platform_key, &block)
57
- self.class.instrument("GraphQL", platform_key, INSTRUMENT_OPTS, &block)
58
- end
59
-
60
- alias :platform_resolve_type :platform_authorized
61
-
62
- def platform_field_key(field)
63
- field.path
64
- end
32
+ include MonitorTrace::Monitor::GraphQLSuffixNames
65
33
 
66
- def platform_authorized_key(type)
67
- "#{type.graphql_name}.authorized"
68
- end
34
+ class Event < MonitorTrace::Monitor::Event
35
+ def start
36
+ layer = ScoutApm::Layer.new("GraphQL", @monitor.name_for(keyword, object))
37
+ layer.subscopable!
38
+ @scout_req = ScoutApm::RequestManager.lookup
39
+ @scout_req.start_layer(layer)
40
+ end
69
41
 
70
- def platform_resolve_type_key(type)
71
- "#{type.graphql_name}.resolve_type"
42
+ def finish
43
+ @scout_req.stop_layer
44
+ end
45
+ end
72
46
  end
73
47
  end
74
48
  end
@@ -1,5 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/platform_tracing"
4
+
3
5
  module GraphQL
4
6
  module Tracing
5
7
  class ScoutTracing < PlatformTracing
@@ -0,0 +1,82 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/monitor_trace"
4
+
5
+ module GraphQL
6
+ module Tracing
7
+ # A tracer for reporting GraphQL-Ruby times to Sentry.
8
+ #
9
+ # @example Installing the tracer
10
+ # class MySchema < GraphQL::Schema
11
+ # trace_with GraphQL::Tracing::SentryTrace
12
+ # end
13
+ # @see MonitorTrace Configuration Options in the parent module
14
+ SentryTrace = MonitorTrace.create_module("sentry")
15
+ module SentryTrace
16
+ class SentryMonitor < MonitorTrace::Monitor
17
+ def instrument(keyword, object)
18
+ return yield unless Sentry.initialized?
19
+
20
+ platform_key = name_for(keyword, object)
21
+
22
+ Sentry.with_child_span(op: platform_key, start_timestamp: Sentry.utc_now.to_f) do |span|
23
+ result = yield
24
+ return result unless span
25
+
26
+ span.finish
27
+ if keyword == :execute
28
+ queries = object.queries
29
+ operation_names = queries.map{|q| operation_name(q) }
30
+ span.set_description(operation_names.join(", "))
31
+
32
+ if queries.size == 1
33
+ query = queries.first
34
+ set_this_txn_name = query.context[:set_sentry_transaction_name]
35
+ if set_this_txn_name == true || (set_this_txn_name.nil? && @set_transaction_name)
36
+ Sentry.configure_scope do |scope|
37
+ scope.set_transaction_name(transaction_name(query))
38
+ end
39
+ end
40
+ span.set_data('graphql.document', query.query_string)
41
+ if query.selected_operation_name
42
+ span.set_data('graphql.operation.name', query.selected_operation_name)
43
+ end
44
+ if query.selected_operation
45
+ span.set_data('graphql.operation.type', query.selected_operation.operation_type)
46
+ end
47
+ end
48
+ end
49
+
50
+ result
51
+ end
52
+ end
53
+
54
+ include MonitorTrace::Monitor::GraphQLPrefixNames
55
+
56
+ private
57
+
58
+ def operation_name(query)
59
+ selected_op = query.selected_operation
60
+ if selected_op
61
+ [selected_op.operation_type, selected_op.name].compact.join(' ')
62
+ else
63
+ 'GraphQL Operation'
64
+ end
65
+ end
66
+
67
+ class Event < MonitorTrace::Monitor::Event
68
+ def start
69
+ if Sentry.initialized? && (@span = Sentry.get_current_scope.get_span)
70
+ span_name = @monitor.name_for(@keyword, @object)
71
+ @span.start_child(op: span_name)
72
+ end
73
+ end
74
+
75
+ def finish
76
+ @span&.finish
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
@@ -1,59 +1,47 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/monitor_trace"
4
+
3
5
  module GraphQL
4
6
  module Tracing
7
+ # A tracer for reporting GraphQL-Ruby times to Statsd.
8
+ # Passing any Statsd client that implements `.time(name) { ... }`
9
+ # and `.timing(name, ms)` will work.
10
+ #
11
+ # @example Installing this tracer
12
+ # # eg:
13
+ # # $statsd = Statsd.new 'localhost', 9125
14
+ # class MySchema < GraphQL::Schema
15
+ # use GraphQL::Tracing::StatsdTrace, statsd: $statsd
16
+ # end
17
+ StatsdTrace = MonitorTrace.create_module("statsd")
5
18
  module StatsdTrace
6
- include PlatformTrace
7
-
8
- # @param statsd [Object] A statsd client
9
- def initialize(statsd:, **rest)
10
- @statsd = statsd
11
- super(**rest)
12
- end
19
+ class StatsdMonitor < MonitorTrace::Monitor
20
+ def initialize(statsd:, **_rest)
21
+ @statsd = statsd
22
+ super
23
+ end
13
24
 
14
- # rubocop:disable Development/NoEvalCop This eval takes static inputs at load-time
25
+ attr_reader :statsd
15
26
 
16
- {
17
- 'lex' => "graphql.lex",
18
- 'parse' => "graphql.parse",
19
- 'validate' => "graphql.validate",
20
- 'analyze_query' => "graphql.analyze_query",
21
- 'analyze_multiplex' => "graphql.analyze_multiplex",
22
- 'execute_multiplex' => "graphql.execute_multiplex",
23
- 'execute_query' => "graphql.execute_query",
24
- 'execute_query_lazy' => "graphql.execute_query_lazy",
25
- }.each do |trace_method, platform_key|
26
- module_eval <<-RUBY, __FILE__, __LINE__
27
- def #{trace_method}(**data)
28
- @statsd.time("#{platform_key}") do
29
- super
30
- end
27
+ def instrument(keyword, object)
28
+ @statsd.time(name_for(keyword, object)) do
29
+ yield
31
30
  end
32
- RUBY
33
- end
34
-
35
- # rubocop:enable Development/NoEvalCop
36
-
37
- def platform_execute_field(platform_key, &block)
38
- @statsd.time(platform_key, &block)
39
- end
31
+ end
40
32
 
41
- def platform_authorized(key, &block)
42
- @statsd.time(key, &block)
43
- end
44
-
45
- alias :platform_resolve_type :platform_authorized
46
-
47
- def platform_field_key(field)
48
- "graphql.#{field.path}"
49
- end
33
+ include MonitorTrace::Monitor::GraphQLPrefixNames
50
34
 
51
- def platform_authorized_key(type)
52
- "graphql.authorized.#{type.graphql_name}"
53
- end
35
+ class Event < MonitorTrace::Monitor::Event
36
+ def start
37
+ @start_time = Process.clock_gettime(Process::CLOCK_MONOTONIC)
38
+ end
54
39
 
55
- def platform_resolve_type_key(type)
56
- "graphql.resolve_type.#{type.graphql_name}"
40
+ def finish
41
+ elapsed = Process.clock_gettime(Process::CLOCK_MONOTONIC) - @start_time
42
+ @monitor.statsd.timing(@monitor.name_for(keyword, object), elapsed)
43
+ end
44
+ end
57
45
  end
58
46
  end
59
47
  end
@@ -1,5 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/tracing/platform_tracing"
4
+
3
5
  module GraphQL
4
6
  module Tracing
5
7
  class StatsdTracing < PlatformTracing
@@ -1,11 +1,14 @@
1
1
  # frozen_string_literal: true
2
+
3
+ require "graphql/tracing"
4
+
2
5
  module GraphQL
3
6
  module Tracing
4
7
  # This is the base class for a `trace` instance whose methods are called during query execution.
5
8
  # "Trace modes" are subclasses of this with custom tracing modules mixed in.
6
9
  #
7
10
  # A trace module may implement any of the methods on `Trace`, being sure to call `super`
8
- # to continue any tracing hooks and call the actual runtime behavior. See {GraphQL::Backtrace::Trace} for example.
11
+ # to continue any tracing hooks and call the actual runtime behavior.
9
12
  #
10
13
  class Trace
11
14
  # @param multiplex [GraphQL::Execution::Multiplex, nil]
@@ -15,10 +18,13 @@ module GraphQL
15
18
  @query = query
16
19
  end
17
20
 
21
+ # The Ruby parser doesn't call this method (`graphql/c_parser` does.)
18
22
  def lex(query_string:)
19
23
  yield
20
24
  end
21
25
 
26
+ # @param query_string [String]
27
+ # @return [void]
22
28
  def parse(query_string:)
23
29
  yield
24
30
  end
@@ -27,6 +33,22 @@ module GraphQL
27
33
  yield
28
34
  end
29
35
 
36
+ def begin_validate(query, validate)
37
+ end
38
+
39
+ def end_validate(query, validate, errors)
40
+ end
41
+
42
+ # @param multiplex [GraphQL::Execution::Multiplex]
43
+ # @param analyzers [Array<Class>]
44
+ # @return [void]
45
+ def begin_analyze_multiplex(multiplex, analyzers); end
46
+ # @param multiplex [GraphQL::Execution::Multiplex]
47
+ # @param analyzers [Array<Class>]
48
+ # @return [void]
49
+ def end_analyze_multiplex(multiplex, analyzers); end
50
+ # @param multiplex [GraphQL::Execution::Multiplex]
51
+ # @return [void]
30
52
  def analyze_multiplex(multiplex:)
31
53
  yield
32
54
  end
@@ -35,6 +57,9 @@ module GraphQL
35
57
  yield
36
58
  end
37
59
 
60
+ # This wraps an entire `.execute` call.
61
+ # @param multiplex [GraphQL::Execution::Multiplex]
62
+ # @return [void]
38
63
  def execute_multiplex(multiplex:)
39
64
  yield
40
65
  end
@@ -47,6 +72,20 @@ module GraphQL
47
72
  yield
48
73
  end
49
74
 
75
+ # GraphQL is about to resolve this field
76
+ # @param field [GraphQL::Schema::Field]
77
+ # @param object [GraphQL::Schema::Object]
78
+ # @param arguments [Hash]
79
+ # @param query [GraphQL::Query]
80
+ def begin_execute_field(field, object, arguments, query); end
81
+ # GraphQL just finished resolving this field
82
+ # @param field [GraphQL::Schema::Field]
83
+ # @param object [GraphQL::Schema::Object]
84
+ # @param arguments [Hash]
85
+ # @param query [GraphQL::Query]
86
+ # @param result [Object]
87
+ def end_execute_field(field, object, arguments, query, result); end
88
+
50
89
  def execute_field(field:, query:, ast_node:, arguments:, object:)
51
90
  yield
52
91
  end
@@ -59,6 +98,22 @@ module GraphQL
59
98
  yield
60
99
  end
61
100
 
101
+ # A call to `.authorized?` is starting
102
+ # @param type [Class<GraphQL::Schema::Object>]
103
+ # @param object [Object]
104
+ # @param context [GraphQL::Query::Context]
105
+ # @return [void]
106
+ def begin_authorized(type, object, context)
107
+ end
108
+ # A call to `.authorized?` just finished
109
+ # @param type [Class<GraphQL::Schema::Object>]
110
+ # @param object [Object]
111
+ # @param context [GraphQL::Query::Context]
112
+ # @param authorized_result [Boolean]
113
+ # @return [void]
114
+ def end_authorized(type, object, context, authorized_result)
115
+ end
116
+
62
117
  def authorized_lazy(query:, type:, object:)
63
118
  yield
64
119
  end
@@ -70,6 +125,62 @@ module GraphQL
70
125
  def resolve_type_lazy(query:, type:, object:)
71
126
  yield
72
127
  end
128
+
129
+ # A call to `.resolve_type` is starting
130
+ # @param type [Class<GraphQL::Schema::Union>, Module<GraphQL::Schema::Interface>]
131
+ # @param value [Object]
132
+ # @param context [GraphQL::Query::Context]
133
+ # @return [void]
134
+ def begin_resolve_type(type, value, context)
135
+ end
136
+
137
+ # A call to `.resolve_type` just ended
138
+ # @param type [Class<GraphQL::Schema::Union>, Module<GraphQL::Schema::Interface>]
139
+ # @param value [Object]
140
+ # @param context [GraphQL::Query::Context]
141
+ # @param resolved_type [Class<GraphQL::Schema::Object>]
142
+ # @return [void]
143
+ def end_resolve_type(type, value, context, resolved_type)
144
+ end
145
+
146
+ # A dataloader run is starting
147
+ # @param dataloader [GraphQL::Dataloader]
148
+ # @return [void]
149
+ def begin_dataloader(dataloader); end
150
+ # A dataloader run has ended
151
+ # @param dataloder [GraphQL::Dataloader]
152
+ # @return [void]
153
+ def end_dataloader(dataloader); end
154
+
155
+ # A source with pending keys is about to fetch
156
+ # @param source [GraphQL::Dataloader::Source]
157
+ # @return [void]
158
+ def begin_dataloader_source(source); end
159
+ # A fetch call has just ended
160
+ # @param source [GraphQL::Dataloader::Source]
161
+ # @return [void]
162
+ def end_dataloader_source(source); end
163
+
164
+ # Called when Dataloader spins up a new fiber for GraphQL execution
165
+ # @param jobs [Array<#call>] Execution steps to run
166
+ # @return [void]
167
+ def dataloader_spawn_execution_fiber(jobs); end
168
+ # Called when Dataloader spins up a new fiber for fetching data
169
+ # @param pending_sources [GraphQL::Dataloader::Source] Instances with pending keys
170
+ # @return [void]
171
+ def dataloader_spawn_source_fiber(pending_sources); end
172
+ # Called when an execution or source fiber terminates
173
+ # @return [void]
174
+ def dataloader_fiber_exit; end
175
+
176
+ # Called when a Dataloader fiber is paused to wait for data
177
+ # @param source [GraphQL::Dataloader::Source] The Source whose `load` call initiated this `yield`
178
+ # @return [void]
179
+ def dataloader_fiber_yield(source); end
180
+ # Called when a Dataloader fiber is resumed because data has been loaded
181
+ # @param source [GraphQL::Dataloader::Source] The Source whose `load` call previously caused this Fiber to wait
182
+ # @return [void]
183
+ def dataloader_fiber_resume(source); end
73
184
  end
74
185
  end
75
186
  end