graphql 1.12.12 → 2.4.8

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.

Potentially problematic release.


This version of graphql might be problematic. Click here for more details.

Files changed (428) hide show
  1. checksums.yaml +4 -4
  2. data/lib/generators/graphql/core.rb +3 -8
  3. data/lib/generators/graphql/enum_generator.rb +4 -10
  4. data/lib/generators/graphql/field_extractor.rb +31 -0
  5. data/lib/generators/graphql/input_generator.rb +50 -0
  6. data/lib/generators/graphql/install/mutation_root_generator.rb +34 -0
  7. data/lib/generators/graphql/{templates → install/templates}/base_mutation.erb +2 -0
  8. data/lib/generators/graphql/{templates → install/templates}/mutation_type.erb +2 -0
  9. data/lib/generators/graphql/install_generator.rb +60 -4
  10. data/lib/generators/graphql/interface_generator.rb +7 -7
  11. data/lib/generators/graphql/mutation_create_generator.rb +22 -0
  12. data/lib/generators/graphql/mutation_delete_generator.rb +22 -0
  13. data/lib/generators/graphql/mutation_generator.rb +5 -30
  14. data/lib/generators/graphql/mutation_update_generator.rb +22 -0
  15. data/lib/generators/graphql/object_generator.rb +10 -38
  16. data/lib/generators/graphql/orm_mutations_base.rb +40 -0
  17. data/lib/generators/graphql/relay.rb +23 -12
  18. data/lib/generators/graphql/scalar_generator.rb +4 -2
  19. data/lib/generators/graphql/templates/base_argument.erb +2 -0
  20. data/lib/generators/graphql/templates/base_connection.erb +2 -0
  21. data/lib/generators/graphql/templates/base_edge.erb +2 -0
  22. data/lib/generators/graphql/templates/base_enum.erb +2 -0
  23. data/lib/generators/graphql/templates/base_field.erb +2 -0
  24. data/lib/generators/graphql/templates/base_input_object.erb +2 -0
  25. data/lib/generators/graphql/templates/base_interface.erb +2 -0
  26. data/lib/generators/graphql/templates/base_object.erb +2 -0
  27. data/lib/generators/graphql/templates/base_resolver.erb +8 -0
  28. data/lib/generators/graphql/templates/base_scalar.erb +2 -0
  29. data/lib/generators/graphql/templates/base_union.erb +2 -0
  30. data/lib/generators/graphql/templates/enum.erb +5 -1
  31. data/lib/generators/graphql/templates/graphql_controller.erb +2 -0
  32. data/lib/generators/graphql/templates/input.erb +9 -0
  33. data/lib/generators/graphql/templates/interface.erb +4 -2
  34. data/lib/generators/graphql/templates/loader.erb +2 -0
  35. data/lib/generators/graphql/templates/mutation.erb +3 -1
  36. data/lib/generators/graphql/templates/mutation_create.erb +20 -0
  37. data/lib/generators/graphql/templates/mutation_delete.erb +20 -0
  38. data/lib/generators/graphql/templates/mutation_update.erb +21 -0
  39. data/lib/generators/graphql/templates/node_type.erb +2 -0
  40. data/lib/generators/graphql/templates/object.erb +4 -2
  41. data/lib/generators/graphql/templates/query_type.erb +2 -0
  42. data/lib/generators/graphql/templates/scalar.erb +3 -1
  43. data/lib/generators/graphql/templates/schema.erb +22 -2
  44. data/lib/generators/graphql/templates/union.erb +4 -2
  45. data/lib/generators/graphql/type_generator.rb +46 -10
  46. data/lib/generators/graphql/union_generator.rb +5 -5
  47. data/lib/graphql/analysis/analyzer.rb +89 -0
  48. data/lib/graphql/analysis/field_usage.rb +65 -28
  49. data/lib/graphql/analysis/max_query_complexity.rb +11 -17
  50. data/lib/graphql/analysis/max_query_depth.rb +13 -19
  51. data/lib/graphql/analysis/query_complexity.rb +156 -61
  52. data/lib/graphql/analysis/query_depth.rb +38 -23
  53. data/lib/graphql/analysis/visitor.rb +283 -0
  54. data/lib/graphql/analysis.rb +90 -6
  55. data/lib/graphql/autoload.rb +38 -0
  56. data/lib/graphql/backtrace/inspect_result.rb +0 -12
  57. data/lib/graphql/backtrace/table.rb +4 -22
  58. data/lib/graphql/backtrace/trace.rb +93 -0
  59. data/lib/graphql/backtrace/tracer.rb +8 -6
  60. data/lib/graphql/backtrace.rb +3 -8
  61. data/lib/graphql/coercion_error.rb +1 -9
  62. data/lib/graphql/current.rb +52 -0
  63. data/lib/graphql/dataloader/async_dataloader.rb +89 -0
  64. data/lib/graphql/dataloader/null_dataloader.rb +4 -2
  65. data/lib/graphql/dataloader/request.rb +5 -0
  66. data/lib/graphql/dataloader/source.rb +125 -33
  67. data/lib/graphql/dataloader.rb +193 -143
  68. data/lib/graphql/date_encoding_error.rb +16 -0
  69. data/lib/graphql/dig.rb +1 -1
  70. data/lib/graphql/duration_encoding_error.rb +16 -0
  71. data/lib/graphql/execution/errors.rb +12 -81
  72. data/lib/graphql/execution/interpreter/argument_value.rb +5 -1
  73. data/lib/graphql/execution/interpreter/arguments.rb +2 -2
  74. data/lib/graphql/execution/interpreter/arguments_cache.rb +33 -36
  75. data/lib/graphql/execution/interpreter/resolve.rb +38 -4
  76. data/lib/graphql/execution/interpreter/runtime/graphql_result.rb +175 -0
  77. data/lib/graphql/execution/interpreter/runtime.rb +447 -403
  78. data/lib/graphql/execution/interpreter.rb +126 -80
  79. data/lib/graphql/execution/lazy.rb +11 -21
  80. data/lib/graphql/execution/lookahead.rb +133 -55
  81. data/lib/graphql/execution/multiplex.rb +4 -172
  82. data/lib/graphql/execution.rb +11 -4
  83. data/lib/graphql/integer_encoding_error.rb +18 -2
  84. data/lib/graphql/introspection/directive_location_enum.rb +2 -2
  85. data/lib/graphql/introspection/directive_type.rb +6 -4
  86. data/lib/graphql/introspection/dynamic_fields.rb +3 -8
  87. data/lib/graphql/introspection/entry_points.rb +11 -18
  88. data/lib/graphql/introspection/enum_value_type.rb +2 -2
  89. data/lib/graphql/introspection/field_type.rb +4 -4
  90. data/lib/graphql/introspection/input_value_type.rb +10 -4
  91. data/lib/graphql/introspection/schema_type.rb +17 -15
  92. data/lib/graphql/introspection/type_type.rb +29 -16
  93. data/lib/graphql/introspection.rb +6 -2
  94. data/lib/graphql/invalid_null_error.rb +1 -1
  95. data/lib/graphql/language/block_string.rb +37 -25
  96. data/lib/graphql/language/cache.rb +13 -0
  97. data/lib/graphql/language/comment.rb +18 -0
  98. data/lib/graphql/language/definition_slice.rb +1 -1
  99. data/lib/graphql/language/document_from_schema_definition.rb +122 -81
  100. data/lib/graphql/language/lexer.rb +364 -1467
  101. data/lib/graphql/language/nodes.rb +197 -106
  102. data/lib/graphql/language/parser.rb +799 -1920
  103. data/lib/graphql/language/printer.rb +372 -160
  104. data/lib/graphql/language/sanitized_printer.rb +25 -27
  105. data/lib/graphql/language/static_visitor.rb +167 -0
  106. data/lib/graphql/language/visitor.rb +188 -141
  107. data/lib/graphql/language.rb +62 -1
  108. data/lib/graphql/load_application_object_failed_error.rb +5 -1
  109. data/lib/graphql/name_validator.rb +0 -4
  110. data/lib/graphql/pagination/active_record_relation_connection.rb +37 -8
  111. data/lib/graphql/pagination/array_connection.rb +8 -6
  112. data/lib/graphql/pagination/connection.rb +61 -7
  113. data/lib/graphql/pagination/connections.rb +22 -23
  114. data/lib/graphql/pagination/mongoid_relation_connection.rb +1 -2
  115. data/lib/graphql/pagination/relation_connection.rb +60 -28
  116. data/lib/graphql/query/context/scoped_context.rb +101 -0
  117. data/lib/graphql/query/context.rb +146 -222
  118. data/lib/graphql/query/input_validation_result.rb +10 -1
  119. data/lib/graphql/query/null_context.rb +15 -32
  120. data/lib/graphql/query/validation_pipeline.rb +15 -39
  121. data/lib/graphql/query/variable_validation_error.rb +3 -3
  122. data/lib/graphql/query/variables.rb +35 -17
  123. data/lib/graphql/query.rb +149 -82
  124. data/lib/graphql/railtie.rb +15 -109
  125. data/lib/graphql/rake_task/validate.rb +1 -1
  126. data/lib/graphql/rake_task.rb +30 -11
  127. data/lib/graphql/relay/range_add.rb +9 -16
  128. data/lib/graphql/relay.rb +0 -15
  129. data/lib/graphql/rubocop/graphql/base_cop.rb +36 -0
  130. data/lib/graphql/rubocop/graphql/default_null_true.rb +43 -0
  131. data/lib/graphql/rubocop/graphql/default_required_true.rb +43 -0
  132. data/lib/graphql/rubocop/graphql/field_type_in_block.rb +144 -0
  133. data/lib/graphql/rubocop/graphql/root_types_in_block.rb +38 -0
  134. data/lib/graphql/rubocop.rb +6 -0
  135. data/lib/graphql/schema/addition.rb +98 -54
  136. data/lib/graphql/schema/always_visible.rb +14 -0
  137. data/lib/graphql/schema/argument.rb +179 -82
  138. data/lib/graphql/schema/base_64_encoder.rb +3 -5
  139. data/lib/graphql/schema/build_from_definition.rb +77 -39
  140. data/lib/graphql/schema/directive/feature.rb +1 -1
  141. data/lib/graphql/schema/directive/flagged.rb +4 -4
  142. data/lib/graphql/schema/directive/include.rb +1 -1
  143. data/lib/graphql/schema/directive/one_of.rb +24 -0
  144. data/lib/graphql/schema/directive/skip.rb +1 -1
  145. data/lib/graphql/schema/directive/specified_by.rb +14 -0
  146. data/lib/graphql/schema/directive/transform.rb +2 -2
  147. data/lib/graphql/schema/directive.rb +36 -22
  148. data/lib/graphql/schema/enum.rb +158 -63
  149. data/lib/graphql/schema/enum_value.rb +12 -21
  150. data/lib/graphql/schema/field/connection_extension.rb +7 -17
  151. data/lib/graphql/schema/field/scope_extension.rb +8 -1
  152. data/lib/graphql/schema/field.rb +521 -359
  153. data/lib/graphql/schema/field_extension.rb +86 -2
  154. data/lib/graphql/schema/find_inherited_value.rb +3 -7
  155. data/lib/graphql/schema/finder.rb +5 -5
  156. data/lib/graphql/schema/has_single_input_argument.rb +160 -0
  157. data/lib/graphql/schema/input_object.rb +148 -99
  158. data/lib/graphql/schema/interface.rb +41 -64
  159. data/lib/graphql/schema/introspection_system.rb +12 -26
  160. data/lib/graphql/schema/late_bound_type.rb +12 -2
  161. data/lib/graphql/schema/list.rb +18 -7
  162. data/lib/graphql/schema/loader.rb +6 -5
  163. data/lib/graphql/schema/member/base_dsl_methods.rb +32 -18
  164. data/lib/graphql/schema/member/build_type.rb +16 -13
  165. data/lib/graphql/schema/member/has_arguments.rb +270 -86
  166. data/lib/graphql/schema/member/has_ast_node.rb +12 -0
  167. data/lib/graphql/schema/member/has_deprecation_reason.rb +3 -4
  168. data/lib/graphql/schema/member/has_directives.rb +81 -61
  169. data/lib/graphql/schema/member/has_fields.rb +169 -31
  170. data/lib/graphql/schema/member/has_interfaces.rb +143 -0
  171. data/lib/graphql/schema/member/has_unresolved_type_error.rb +5 -1
  172. data/lib/graphql/schema/member/has_validators.rb +32 -6
  173. data/lib/graphql/schema/member/relay_shortcuts.rb +47 -2
  174. data/lib/graphql/schema/member/scoped.rb +19 -0
  175. data/lib/graphql/schema/member/type_system_helpers.rb +16 -0
  176. data/lib/graphql/schema/member/validates_input.rb +6 -6
  177. data/lib/graphql/schema/member.rb +1 -6
  178. data/lib/graphql/schema/mutation.rb +7 -9
  179. data/lib/graphql/schema/non_null.rb +7 -7
  180. data/lib/graphql/schema/object.rb +38 -119
  181. data/lib/graphql/schema/printer.rb +24 -25
  182. data/lib/graphql/schema/relay_classic_mutation.rb +13 -91
  183. data/lib/graphql/schema/resolver/has_payload_type.rb +46 -11
  184. data/lib/graphql/schema/resolver.rb +118 -115
  185. data/lib/graphql/schema/scalar.rb +20 -21
  186. data/lib/graphql/schema/subscription.rb +95 -21
  187. data/lib/graphql/schema/timeout.rb +25 -29
  188. data/lib/graphql/schema/type_expression.rb +2 -2
  189. data/lib/graphql/schema/type_membership.rb +21 -4
  190. data/lib/graphql/schema/union.rb +16 -16
  191. data/lib/graphql/schema/unique_within_type.rb +1 -1
  192. data/lib/graphql/schema/validator/all_validator.rb +62 -0
  193. data/lib/graphql/schema/validator/allow_blank_validator.rb +29 -0
  194. data/lib/graphql/schema/validator/allow_null_validator.rb +26 -0
  195. data/lib/graphql/schema/validator/exclusion_validator.rb +3 -1
  196. data/lib/graphql/schema/validator/format_validator.rb +4 -5
  197. data/lib/graphql/schema/validator/inclusion_validator.rb +3 -1
  198. data/lib/graphql/schema/validator/length_validator.rb +5 -3
  199. data/lib/graphql/schema/validator/numericality_validator.rb +13 -2
  200. data/lib/graphql/schema/validator/required_validator.rb +56 -18
  201. data/lib/graphql/schema/validator.rb +38 -28
  202. data/lib/graphql/schema/visibility/migration.rb +188 -0
  203. data/lib/graphql/schema/visibility/profile.rb +359 -0
  204. data/lib/graphql/schema/visibility/visit.rb +190 -0
  205. data/lib/graphql/schema/visibility.rb +294 -0
  206. data/lib/graphql/schema/warden.rb +423 -134
  207. data/lib/graphql/schema/wrapper.rb +0 -5
  208. data/lib/graphql/schema.rb +1015 -1057
  209. data/lib/graphql/static_validation/all_rules.rb +3 -1
  210. data/lib/graphql/static_validation/base_visitor.rb +15 -28
  211. data/lib/graphql/static_validation/definition_dependencies.rb +7 -2
  212. data/lib/graphql/static_validation/error.rb +3 -1
  213. data/lib/graphql/static_validation/literal_validator.rb +24 -7
  214. data/lib/graphql/static_validation/rules/argument_literals_are_compatible.rb +1 -1
  215. data/lib/graphql/static_validation/rules/argument_names_are_unique.rb +1 -1
  216. data/lib/graphql/static_validation/rules/arguments_are_defined.rb +4 -3
  217. data/lib/graphql/static_validation/rules/directives_are_defined.rb +13 -7
  218. data/lib/graphql/static_validation/rules/directives_are_in_valid_locations.rb +15 -13
  219. data/lib/graphql/static_validation/rules/fields_are_defined_on_type.rb +12 -2
  220. data/lib/graphql/static_validation/rules/fields_have_appropriate_selections.rb +13 -5
  221. data/lib/graphql/static_validation/rules/fields_will_merge.rb +62 -35
  222. data/lib/graphql/static_validation/rules/fields_will_merge_error.rb +25 -4
  223. data/lib/graphql/static_validation/rules/fragment_spreads_are_possible.rb +3 -3
  224. data/lib/graphql/static_validation/rules/fragment_types_exist.rb +12 -2
  225. data/lib/graphql/static_validation/rules/fragments_are_finite.rb +2 -2
  226. data/lib/graphql/static_validation/rules/fragments_are_on_composite_types.rb +1 -1
  227. data/lib/graphql/static_validation/rules/mutation_root_exists.rb +1 -1
  228. data/lib/graphql/static_validation/rules/no_definitions_are_present.rb +1 -1
  229. data/lib/graphql/static_validation/rules/one_of_input_objects_are_valid.rb +66 -0
  230. data/lib/graphql/static_validation/rules/one_of_input_objects_are_valid_error.rb +29 -0
  231. data/lib/graphql/static_validation/rules/query_root_exists.rb +17 -0
  232. data/lib/graphql/static_validation/rules/query_root_exists_error.rb +26 -0
  233. data/lib/graphql/static_validation/rules/required_arguments_are_present.rb +7 -5
  234. data/lib/graphql/static_validation/rules/required_input_object_attributes_are_present.rb +5 -5
  235. data/lib/graphql/static_validation/rules/subscription_root_exists.rb +1 -1
  236. data/lib/graphql/static_validation/rules/unique_directives_per_location.rb +14 -8
  237. data/lib/graphql/static_validation/rules/variable_default_values_are_correctly_typed.rb +18 -27
  238. data/lib/graphql/static_validation/rules/variable_names_are_unique.rb +1 -1
  239. data/lib/graphql/static_validation/rules/variable_usages_are_allowed.rb +14 -8
  240. data/lib/graphql/static_validation/rules/variables_are_input_types.rb +11 -2
  241. data/lib/graphql/static_validation/validation_context.rb +32 -6
  242. data/lib/graphql/static_validation/validator.rb +11 -27
  243. data/lib/graphql/static_validation.rb +0 -3
  244. data/lib/graphql/string_encoding_error.rb +13 -3
  245. data/lib/graphql/subscriptions/action_cable_subscriptions.rb +49 -11
  246. data/lib/graphql/subscriptions/broadcast_analyzer.rb +11 -5
  247. data/lib/graphql/subscriptions/default_subscription_resolve_extension.rb +40 -1
  248. data/lib/graphql/subscriptions/event.rb +87 -38
  249. data/lib/graphql/subscriptions/serialize.rb +27 -3
  250. data/lib/graphql/subscriptions.rb +63 -49
  251. data/lib/graphql/testing/helpers.rb +155 -0
  252. data/lib/graphql/testing.rb +2 -0
  253. data/lib/graphql/tracing/active_support_notifications_trace.rb +16 -0
  254. data/lib/graphql/tracing/active_support_notifications_tracing.rb +6 -20
  255. data/lib/graphql/tracing/appoptics_trace.rb +253 -0
  256. data/lib/graphql/tracing/appoptics_tracing.rb +4 -2
  257. data/lib/graphql/tracing/appsignal_trace.rb +79 -0
  258. data/lib/graphql/tracing/appsignal_tracing.rb +17 -0
  259. data/lib/graphql/tracing/call_legacy_tracers.rb +66 -0
  260. data/lib/graphql/tracing/data_dog_trace.rb +185 -0
  261. data/lib/graphql/tracing/data_dog_tracing.rb +27 -15
  262. data/lib/graphql/{execution/instrumentation.rb → tracing/legacy_hooks_trace.rb} +11 -28
  263. data/lib/graphql/tracing/legacy_trace.rb +12 -0
  264. data/lib/graphql/tracing/new_relic_trace.rb +77 -0
  265. data/lib/graphql/tracing/new_relic_tracing.rb +2 -0
  266. data/lib/graphql/tracing/notifications_trace.rb +45 -0
  267. data/lib/graphql/tracing/notifications_tracing.rb +61 -0
  268. data/lib/graphql/tracing/null_trace.rb +9 -0
  269. data/lib/graphql/tracing/platform_trace.rb +118 -0
  270. data/lib/graphql/tracing/platform_tracing.rb +46 -49
  271. data/lib/graphql/tracing/{prometheus_tracing → prometheus_trace}/graphql_collector.rb +6 -2
  272. data/lib/graphql/tracing/prometheus_trace.rb +94 -0
  273. data/lib/graphql/tracing/prometheus_tracing.rb +5 -3
  274. data/lib/graphql/tracing/scout_trace.rb +74 -0
  275. data/lib/graphql/tracing/scout_tracing.rb +2 -0
  276. data/lib/graphql/tracing/sentry_trace.rb +114 -0
  277. data/lib/graphql/tracing/statsd_trace.rb +58 -0
  278. data/lib/graphql/tracing/statsd_tracing.rb +2 -0
  279. data/lib/graphql/tracing/trace.rb +79 -0
  280. data/lib/graphql/tracing.rb +29 -52
  281. data/lib/graphql/type_kinds.rb +7 -4
  282. data/lib/graphql/types/big_int.rb +5 -1
  283. data/lib/graphql/types/int.rb +1 -1
  284. data/lib/graphql/types/iso_8601_date.rb +17 -6
  285. data/lib/graphql/types/iso_8601_date_time.rb +12 -1
  286. data/lib/graphql/types/iso_8601_duration.rb +77 -0
  287. data/lib/graphql/types/relay/base_connection.rb +16 -6
  288. data/lib/graphql/types/relay/connection_behaviors.rb +92 -32
  289. data/lib/graphql/types/relay/edge_behaviors.rb +46 -7
  290. data/lib/graphql/types/relay/has_node_field.rb +2 -2
  291. data/lib/graphql/types/relay/has_nodes_field.rb +2 -2
  292. data/lib/graphql/types/relay/node_behaviors.rb +12 -2
  293. data/lib/graphql/types/relay/page_info_behaviors.rb +11 -2
  294. data/lib/graphql/types/relay.rb +0 -3
  295. data/lib/graphql/types/string.rb +2 -2
  296. data/lib/graphql/types.rb +18 -10
  297. data/lib/graphql/unauthorized_enum_value_error.rb +13 -0
  298. data/lib/graphql/unauthorized_error.rb +1 -1
  299. data/lib/graphql/version.rb +1 -1
  300. data/lib/graphql.rb +82 -137
  301. data/readme.md +13 -6
  302. metadata +127 -186
  303. data/lib/graphql/analysis/analyze_query.rb +0 -98
  304. data/lib/graphql/analysis/ast/analyzer.rb +0 -84
  305. data/lib/graphql/analysis/ast/field_usage.rb +0 -28
  306. data/lib/graphql/analysis/ast/max_query_complexity.rb +0 -23
  307. data/lib/graphql/analysis/ast/max_query_depth.rb +0 -22
  308. data/lib/graphql/analysis/ast/query_complexity.rb +0 -234
  309. data/lib/graphql/analysis/ast/query_depth.rb +0 -56
  310. data/lib/graphql/analysis/ast/visitor.rb +0 -268
  311. data/lib/graphql/analysis/ast.rb +0 -91
  312. data/lib/graphql/analysis/reducer_state.rb +0 -48
  313. data/lib/graphql/argument.rb +0 -131
  314. data/lib/graphql/authorization.rb +0 -82
  315. data/lib/graphql/backtrace/legacy_tracer.rb +0 -56
  316. data/lib/graphql/backwards_compatibility.rb +0 -61
  317. data/lib/graphql/base_type.rb +0 -230
  318. data/lib/graphql/boolean_type.rb +0 -2
  319. data/lib/graphql/compatibility/execution_specification/counter_schema.rb +0 -53
  320. data/lib/graphql/compatibility/execution_specification/specification_schema.rb +0 -200
  321. data/lib/graphql/compatibility/execution_specification.rb +0 -436
  322. data/lib/graphql/compatibility/lazy_execution_specification/lazy_schema.rb +0 -111
  323. data/lib/graphql/compatibility/lazy_execution_specification.rb +0 -215
  324. data/lib/graphql/compatibility/query_parser_specification/parse_error_specification.rb +0 -87
  325. data/lib/graphql/compatibility/query_parser_specification/query_assertions.rb +0 -79
  326. data/lib/graphql/compatibility/query_parser_specification.rb +0 -266
  327. data/lib/graphql/compatibility/schema_parser_specification.rb +0 -682
  328. data/lib/graphql/compatibility.rb +0 -5
  329. data/lib/graphql/define/assign_argument.rb +0 -12
  330. data/lib/graphql/define/assign_connection.rb +0 -13
  331. data/lib/graphql/define/assign_enum_value.rb +0 -18
  332. data/lib/graphql/define/assign_global_id_field.rb +0 -11
  333. data/lib/graphql/define/assign_mutation_function.rb +0 -34
  334. data/lib/graphql/define/assign_object_field.rb +0 -42
  335. data/lib/graphql/define/defined_object_proxy.rb +0 -53
  336. data/lib/graphql/define/instance_definable.rb +0 -240
  337. data/lib/graphql/define/no_definition_error.rb +0 -7
  338. data/lib/graphql/define/non_null_with_bang.rb +0 -16
  339. data/lib/graphql/define/type_definer.rb +0 -31
  340. data/lib/graphql/define.rb +0 -31
  341. data/lib/graphql/deprecated_dsl.rb +0 -47
  342. data/lib/graphql/deprecation.rb +0 -13
  343. data/lib/graphql/directive/deprecated_directive.rb +0 -2
  344. data/lib/graphql/directive/include_directive.rb +0 -2
  345. data/lib/graphql/directive/skip_directive.rb +0 -2
  346. data/lib/graphql/directive.rb +0 -111
  347. data/lib/graphql/enum_type.rb +0 -129
  348. data/lib/graphql/execution/execute.rb +0 -333
  349. data/lib/graphql/execution/flatten.rb +0 -40
  350. data/lib/graphql/execution/lazy/resolve.rb +0 -91
  351. data/lib/graphql/execution/typecast.rb +0 -50
  352. data/lib/graphql/field/resolve.rb +0 -59
  353. data/lib/graphql/field.rb +0 -226
  354. data/lib/graphql/filter.rb +0 -53
  355. data/lib/graphql/float_type.rb +0 -2
  356. data/lib/graphql/function.rb +0 -128
  357. data/lib/graphql/id_type.rb +0 -2
  358. data/lib/graphql/input_object_type.rb +0 -138
  359. data/lib/graphql/int_type.rb +0 -2
  360. data/lib/graphql/interface_type.rb +0 -72
  361. data/lib/graphql/internal_representation/document.rb +0 -27
  362. data/lib/graphql/internal_representation/node.rb +0 -206
  363. data/lib/graphql/internal_representation/print.rb +0 -51
  364. data/lib/graphql/internal_representation/rewrite.rb +0 -184
  365. data/lib/graphql/internal_representation/scope.rb +0 -88
  366. data/lib/graphql/internal_representation/visit.rb +0 -36
  367. data/lib/graphql/internal_representation.rb +0 -7
  368. data/lib/graphql/language/lexer.rl +0 -262
  369. data/lib/graphql/language/parser.y +0 -543
  370. data/lib/graphql/language/token.rb +0 -38
  371. data/lib/graphql/list_type.rb +0 -80
  372. data/lib/graphql/non_null_type.rb +0 -71
  373. data/lib/graphql/object_type.rb +0 -130
  374. data/lib/graphql/query/arguments.rb +0 -189
  375. data/lib/graphql/query/arguments_cache.rb +0 -24
  376. data/lib/graphql/query/executor.rb +0 -52
  377. data/lib/graphql/query/literal_input.rb +0 -136
  378. data/lib/graphql/query/serial_execution/field_resolution.rb +0 -92
  379. data/lib/graphql/query/serial_execution/operation_resolution.rb +0 -19
  380. data/lib/graphql/query/serial_execution/selection_resolution.rb +0 -23
  381. data/lib/graphql/query/serial_execution/value_resolution.rb +0 -87
  382. data/lib/graphql/query/serial_execution.rb +0 -40
  383. data/lib/graphql/relay/array_connection.rb +0 -83
  384. data/lib/graphql/relay/base_connection.rb +0 -189
  385. data/lib/graphql/relay/connection_instrumentation.rb +0 -54
  386. data/lib/graphql/relay/connection_resolve.rb +0 -43
  387. data/lib/graphql/relay/connection_type.rb +0 -41
  388. data/lib/graphql/relay/edge.rb +0 -27
  389. data/lib/graphql/relay/edge_type.rb +0 -19
  390. data/lib/graphql/relay/edges_instrumentation.rb +0 -40
  391. data/lib/graphql/relay/global_id_resolve.rb +0 -18
  392. data/lib/graphql/relay/mongo_relation_connection.rb +0 -50
  393. data/lib/graphql/relay/mutation/instrumentation.rb +0 -23
  394. data/lib/graphql/relay/mutation/resolve.rb +0 -56
  395. data/lib/graphql/relay/mutation/result.rb +0 -38
  396. data/lib/graphql/relay/mutation.rb +0 -106
  397. data/lib/graphql/relay/node.rb +0 -39
  398. data/lib/graphql/relay/page_info.rb +0 -7
  399. data/lib/graphql/relay/relation_connection.rb +0 -188
  400. data/lib/graphql/relay/type_extensions.rb +0 -32
  401. data/lib/graphql/scalar_type.rb +0 -91
  402. data/lib/graphql/schema/base_64_bp.rb +0 -26
  403. data/lib/graphql/schema/catchall_middleware.rb +0 -35
  404. data/lib/graphql/schema/default_parse_error.rb +0 -10
  405. data/lib/graphql/schema/default_type_error.rb +0 -17
  406. data/lib/graphql/schema/invalid_type_error.rb +0 -7
  407. data/lib/graphql/schema/member/accepts_definition.rb +0 -152
  408. data/lib/graphql/schema/member/cached_graphql_definition.rb +0 -31
  409. data/lib/graphql/schema/member/instrumentation.rb +0 -131
  410. data/lib/graphql/schema/middleware_chain.rb +0 -82
  411. data/lib/graphql/schema/possible_types.rb +0 -44
  412. data/lib/graphql/schema/rescue_middleware.rb +0 -60
  413. data/lib/graphql/schema/timeout_middleware.rb +0 -88
  414. data/lib/graphql/schema/traversal.rb +0 -228
  415. data/lib/graphql/schema/validation.rb +0 -313
  416. data/lib/graphql/static_validation/default_visitor.rb +0 -15
  417. data/lib/graphql/static_validation/no_validate_visitor.rb +0 -10
  418. data/lib/graphql/static_validation/type_stack.rb +0 -216
  419. data/lib/graphql/string_type.rb +0 -2
  420. data/lib/graphql/subscriptions/instrumentation.rb +0 -79
  421. data/lib/graphql/subscriptions/subscription_root.rb +0 -76
  422. data/lib/graphql/tracing/skylight_tracing.rb +0 -70
  423. data/lib/graphql/types/relay/default_relay.rb +0 -27
  424. data/lib/graphql/types/relay/node_field.rb +0 -25
  425. data/lib/graphql/types/relay/nodes_field.rb +0 -27
  426. data/lib/graphql/union_type.rb +0 -115
  427. data/lib/graphql/upgrader/member.rb +0 -937
  428. data/lib/graphql/upgrader/schema.rb +0 -38
@@ -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 DataDogTracing < PlatformTracing
@@ -15,17 +17,23 @@ module GraphQL
15
17
  }
16
18
 
17
19
  def platform_trace(platform_key, key, data)
18
- tracer.trace(platform_key, service: service_name) do |span|
19
- span.span_type = 'custom'
20
+ tracer.trace(platform_key, service: options[:service], type: 'custom') do |span|
21
+ span.set_tag('component', 'graphql')
22
+ span.set_tag('operation', key)
20
23
 
21
24
  if key == 'execute_multiplex'
22
25
  operations = data[:multiplex].queries.map(&:selected_operation_name).join(', ')
23
- span.resource = operations unless operations.empty?
24
26
 
25
- # For top span of query, set the analytics sample rate tag, if available.
26
- if analytics_enabled?
27
- Datadog::Contrib::Analytics.set_sample_rate(span, analytics_sample_rate)
27
+ resource = if operations.empty?
28
+ first_query = data[:multiplex].queries.first
29
+ fallback_transaction_name(first_query && first_query.context)
30
+ else
31
+ operations
28
32
  end
33
+ span.resource = resource if resource
34
+
35
+ # [Deprecated] will be removed in the future
36
+ span.set_metric('_dd1.sr.eausr', analytics_sample_rate) if analytics_enabled?
29
37
  end
30
38
 
31
39
  if key == 'execute_query'
@@ -34,29 +42,33 @@ module GraphQL
34
42
  span.set_tag(:query_string, data[:query].query_string)
35
43
  end
36
44
 
45
+ prepare_span(key, data, span)
46
+
37
47
  yield
38
48
  end
39
49
  end
40
50
 
41
- def service_name
42
- options.fetch(:service, 'ruby-graphql')
51
+ # Implement this method in a subclass to apply custom tags to datadog spans
52
+ # @param key [String] The event being traced
53
+ # @param data [Hash] The runtime data for this event (@see GraphQL::Tracing for keys for each event)
54
+ # @param span [Datadog::Tracing::SpanOperation] The datadog span for this event
55
+ def prepare_span(key, data, span)
43
56
  end
44
57
 
45
58
  def tracer
46
- options.fetch(:tracer, Datadog.tracer)
47
- end
59
+ default_tracer = defined?(Datadog::Tracing) ? Datadog::Tracing : Datadog.tracer
48
60
 
49
- def analytics_available?
50
- defined?(Datadog::Contrib::Analytics) \
51
- && Datadog::Contrib::Analytics.respond_to?(:enabled?) \
52
- && Datadog::Contrib::Analytics.respond_to?(:set_sample_rate)
61
+ # [Deprecated] options[:tracer] will be removed in the future
62
+ options.fetch(:tracer, default_tracer)
53
63
  end
54
64
 
55
65
  def analytics_enabled?
56
- analytics_available? && Datadog::Contrib::Analytics.enabled?(options.fetch(:analytics_enabled, false))
66
+ # [Deprecated] options[:analytics_enabled] will be removed in the future
67
+ options.fetch(:analytics_enabled, false)
57
68
  end
58
69
 
59
70
  def analytics_sample_rate
71
+ # [Deprecated] options[:analytics_sample_rate] will be removed in the future
60
72
  options.fetch(:analytics_sample_rate, 1.0)
61
73
  end
62
74
 
@@ -1,38 +1,21 @@
1
1
  # frozen_string_literal: true
2
- module GraphQL
3
- module Execution
4
- module Instrumentation
5
- # This function implements the instrumentation policy:
6
- #
7
- # - Instrumenters are a stack; the first `before_query` will have the last `after_query`
8
- # - If a `before_` hook returned without an error, its corresponding `after_` hook will run.
9
- # - If the `before_` hook did _not_ run, the `after_` hook will not be called.
10
- #
11
- # When errors are raised from `after_` hooks:
12
- # - Subsequent `after_` hooks _are_ called
13
- # - The first raised error is captured; later errors are ignored
14
- # - If an error was capture, it's re-raised after all hooks are finished
15
- #
16
- # Partial runs of instrumentation are possible:
17
- # - If a `before_multiplex` hook raises an error, no `before_query` hooks will run
18
- # - If a `before_query` hook raises an error, subsequent `before_query` hooks will not run (on any query)
19
- def self.apply_instrumenters(multiplex)
20
- schema = multiplex.schema
21
- queries = multiplex.queries
22
- query_instrumenters = schema.instrumenters[:query]
23
- multiplex_instrumenters = schema.instrumenters[:multiplex]
24
2
 
3
+ module GraphQL
4
+ module Tracing
5
+ module LegacyHooksTrace
6
+ def execute_multiplex(multiplex:)
7
+ multiplex_instrumenters = multiplex.schema.instrumenters[:multiplex]
8
+ query_instrumenters = multiplex.schema.instrumenters[:query]
25
9
  # First, run multiplex instrumentation, then query instrumentation for each query
26
- call_hooks(multiplex_instrumenters, multiplex, :before_multiplex, :after_multiplex) do
27
- each_query_call_hooks(query_instrumenters, queries) do
28
- # Let them be executed
29
- yield
10
+ RunHooks.call_hooks(multiplex_instrumenters, multiplex, :before_multiplex, :after_multiplex) do
11
+ RunHooks.each_query_call_hooks(query_instrumenters, multiplex.queries) do
12
+ super
30
13
  end
31
14
  end
32
15
  end
33
16
 
34
- class << self
35
- private
17
+ module RunHooks
18
+ module_function
36
19
  # Call the before_ hooks of each query,
37
20
  # Then yield if no errors.
38
21
  # `call_hooks` takes care of appropriate cleanup.
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/trace"
4
+ require "graphql/tracing/call_legacy_tracers"
5
+
6
+ module GraphQL
7
+ module Tracing
8
+ class LegacyTrace < Trace
9
+ include CallLegacyTracers
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/platform_trace"
4
+
5
+ module GraphQL
6
+ module Tracing
7
+ module NewRelicTrace
8
+ include PlatformTrace
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_new_relic_transaction_name]`.
13
+ def initialize(set_transaction_name: false, **_rest)
14
+ @set_transaction_name = set_transaction_name
15
+ super
16
+ end
17
+
18
+ def execute_query(query:)
19
+ set_this_txn_name = query.context[:set_new_relic_transaction_name]
20
+ if set_this_txn_name == true || (set_this_txn_name.nil? && @set_transaction_name)
21
+ NewRelic::Agent.set_transaction_name(transaction_name(query))
22
+ end
23
+ NewRelic::Agent::MethodTracerHelpers.trace_execution_scoped("GraphQL/execute") do
24
+ super
25
+ end
26
+ end
27
+
28
+ {
29
+ "lex" => "GraphQL/lex",
30
+ "parse" => "GraphQL/parse",
31
+ "validate" => "GraphQL/validate",
32
+ "analyze_query" => "GraphQL/analyze",
33
+ "analyze_multiplex" => "GraphQL/analyze",
34
+ "execute_multiplex" => "GraphQL/execute",
35
+ "execute_query_lazy" => "GraphQL/execute",
36
+ }.each do |trace_method, platform_key|
37
+ module_eval <<-RUBY, __FILE__, __LINE__
38
+ def #{trace_method}(**_keys)
39
+ NewRelic::Agent::MethodTracerHelpers.trace_execution_scoped("#{platform_key}") do
40
+ super
41
+ end
42
+ end
43
+ RUBY
44
+ end
45
+
46
+ def platform_execute_field(platform_key)
47
+ NewRelic::Agent::MethodTracerHelpers.trace_execution_scoped(platform_key) do
48
+ yield
49
+ end
50
+ end
51
+
52
+ def platform_authorized(platform_key)
53
+ NewRelic::Agent::MethodTracerHelpers.trace_execution_scoped(platform_key) do
54
+ yield
55
+ end
56
+ end
57
+
58
+ def platform_resolve_type(platform_key)
59
+ NewRelic::Agent::MethodTracerHelpers.trace_execution_scoped(platform_key) do
60
+ yield
61
+ end
62
+ end
63
+
64
+ def platform_field_key(field)
65
+ "GraphQL/#{field.owner.graphql_name}/#{field.graphql_name}"
66
+ end
67
+
68
+ def platform_authorized_key(type)
69
+ "GraphQL/Authorize/#{type.graphql_name}"
70
+ end
71
+
72
+ def platform_resolve_type_key(type)
73
+ "GraphQL/ResolveType/#{type.graphql_name}"
74
+ end
75
+ end
76
+ end
77
+ 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 NewRelicTracing < PlatformTracing
@@ -0,0 +1,45 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/platform_trace"
4
+
5
+ module GraphQL
6
+ module Tracing
7
+ # This implementation forwards events to a notification handler (i.e.
8
+ # ActiveSupport::Notifications or Dry::Monitor::Notifications)
9
+ # with a `graphql` suffix.
10
+ module NotificationsTrace
11
+ # Initialize a new NotificationsTracing instance
12
+ #
13
+ # @param engine [#instrument(key, metadata, block)] The notifications engine to use
14
+ def initialize(engine:, **rest)
15
+ @notifications_engine = engine
16
+ super
17
+ end
18
+
19
+ {
20
+ "lex" => "lex.graphql",
21
+ "parse" => "parse.graphql",
22
+ "validate" => "validate.graphql",
23
+ "analyze_multiplex" => "analyze_multiplex.graphql",
24
+ "analyze_query" => "analyze_query.graphql",
25
+ "execute_multiplex" => "execute_multiplex.graphql",
26
+ "execute_query" => "execute_query.graphql",
27
+ "execute_query_lazy" => "execute_query_lazy.graphql",
28
+ "execute_field" => "execute_field.graphql",
29
+ "execute_field_lazy" => "execute_field_lazy.graphql",
30
+ "authorized" => "authorized.graphql",
31
+ "authorized_lazy" => "authorized_lazy.graphql",
32
+ "resolve_type" => "resolve_type.graphql",
33
+ "resolve_type_lazy" => "resolve_type.graphql",
34
+ }.each do |trace_method, platform_key|
35
+ module_eval <<-RUBY, __FILE__, __LINE__
36
+ def #{trace_method}(**metadata, &block)
37
+ @notifications_engine.instrument("#{platform_key}", metadata) { super(**metadata, &block) }
38
+ end
39
+ RUBY
40
+ end
41
+
42
+ include PlatformTrace
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,61 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/platform_tracing"
4
+
5
+ module GraphQL
6
+ module Tracing
7
+ # This implementation forwards events to a notification handler (i.e.
8
+ # ActiveSupport::Notifications or Dry::Monitor::Notifications)
9
+ # with a `graphql` suffix.
10
+ #
11
+ # @see KEYS for event names
12
+ class NotificationsTracing
13
+ # A cache of frequently-used keys to avoid needless string allocations
14
+ KEYS = {
15
+ "lex" => "lex.graphql",
16
+ "parse" => "parse.graphql",
17
+ "validate" => "validate.graphql",
18
+ "analyze_multiplex" => "analyze_multiplex.graphql",
19
+ "analyze_query" => "analyze_query.graphql",
20
+ "execute_query" => "execute_query.graphql",
21
+ "execute_query_lazy" => "execute_query_lazy.graphql",
22
+ "execute_field" => "execute_field.graphql",
23
+ "execute_field_lazy" => "execute_field_lazy.graphql",
24
+ "authorized" => "authorized.graphql",
25
+ "authorized_lazy" => "authorized_lazy.graphql",
26
+ "resolve_type" => "resolve_type.graphql",
27
+ "resolve_type_lazy" => "resolve_type.graphql",
28
+ }
29
+
30
+ MAX_KEYS_SIZE = 100
31
+
32
+ # Initialize a new NotificationsTracing instance
33
+ #
34
+ # @param [Object] notifications_engine The notifications engine to use
35
+ def initialize(notifications_engine)
36
+ @notifications_engine = notifications_engine
37
+ end
38
+
39
+ # Sends a GraphQL tracing event to the notification handler
40
+ #
41
+ # @example
42
+ # . notifications_engine = Dry::Monitor::Notifications.new(:graphql)
43
+ # . tracer = GraphQL::Tracing::NotificationsTracing.new(notifications_engine)
44
+ # . tracer.trace("lex") { ... }
45
+ #
46
+ # @param [string] key The key for the event
47
+ # @param [Hash] metadata The metadata for the event
48
+ # @yield The block to execute for the event
49
+ def trace(key, metadata, &blk)
50
+ prefixed_key = KEYS[key] || "#{key}.graphql"
51
+
52
+ # Cache the new keys while making sure not to induce a memory leak
53
+ if KEYS.size < MAX_KEYS_SIZE
54
+ KEYS[key] ||= prefixed_key
55
+ end
56
+
57
+ @notifications_engine.instrument(prefixed_key, metadata, &blk)
58
+ end
59
+ end
60
+ end
61
+ end
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql/tracing/trace"
4
+
5
+ module GraphQL
6
+ module Tracing
7
+ NullTrace = Trace.new
8
+ end
9
+ end
@@ -0,0 +1,118 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module Tracing
5
+ module PlatformTrace
6
+ def initialize(trace_scalars: false, **_options)
7
+ @trace_scalars = trace_scalars
8
+
9
+ @platform_key_cache = Hash.new { |h, mod| h[mod] = mod::KeyCache.new }
10
+ super
11
+ end
12
+
13
+ module BaseKeyCache
14
+ def initialize
15
+ @platform_field_key_cache = Hash.new { |h, k| h[k] = platform_field_key(k) }
16
+ @platform_authorized_key_cache = Hash.new { |h, k| h[k] = platform_authorized_key(k) }
17
+ @platform_resolve_type_key_cache = Hash.new { |h, k| h[k] = platform_resolve_type_key(k) }
18
+ end
19
+
20
+ attr_reader :platform_field_key_cache, :platform_authorized_key_cache, :platform_resolve_type_key_cache
21
+ end
22
+
23
+
24
+ def platform_execute_field_lazy(*args, &block)
25
+ platform_execute_field(*args, &block)
26
+ end
27
+
28
+ def platform_authorized_lazy(key, &block)
29
+ platform_authorized(key, &block)
30
+ end
31
+
32
+ def platform_resolve_type_lazy(key, &block)
33
+ platform_resolve_type(key, &block)
34
+ end
35
+
36
+ def self.included(child_class)
37
+ key_methods_class = Class.new {
38
+ include(child_class)
39
+ include(BaseKeyCache)
40
+ }
41
+ child_class.const_set(:KeyCache, key_methods_class)
42
+ [:execute_field, :execute_field_lazy].each do |field_trace_method|
43
+ if !child_class.method_defined?(field_trace_method)
44
+ child_class.module_eval <<-RUBY, __FILE__, __LINE__
45
+ def #{field_trace_method}(query:, field:, ast_node:, arguments:, object:)
46
+ return_type = field.type.unwrap
47
+ trace_field = if return_type.kind.scalar? || return_type.kind.enum?
48
+ (field.trace.nil? && @trace_scalars) || field.trace
49
+ else
50
+ true
51
+ end
52
+ platform_key = if trace_field
53
+ @platform_key_cache[#{child_class}].platform_field_key_cache[field]
54
+ else
55
+ nil
56
+ end
57
+ if platform_key && trace_field
58
+ platform_#{field_trace_method}(platform_key) do
59
+ super
60
+ end
61
+ else
62
+ super
63
+ end
64
+ end
65
+ RUBY
66
+ end
67
+ end
68
+
69
+
70
+ [:authorized, :authorized_lazy].each do |auth_trace_method|
71
+ if !child_class.method_defined?(auth_trace_method)
72
+ child_class.module_eval <<-RUBY, __FILE__, __LINE__
73
+ def #{auth_trace_method}(type:, query:, object:)
74
+ platform_key = @platform_key_cache[#{child_class}].platform_authorized_key_cache[type]
75
+ platform_#{auth_trace_method}(platform_key) do
76
+ super
77
+ end
78
+ end
79
+ RUBY
80
+ end
81
+ end
82
+
83
+ [:resolve_type, :resolve_type_lazy].each do |rt_trace_method|
84
+ if !child_class.method_defined?(rt_trace_method)
85
+ child_class.module_eval <<-RUBY, __FILE__, __LINE__
86
+ def #{rt_trace_method}(query:, type:, object:)
87
+ platform_key = @platform_key_cache[#{child_class}].platform_resolve_type_key_cache[type]
88
+ platform_#{rt_trace_method}(platform_key) do
89
+ super
90
+ end
91
+ end
92
+ RUBY
93
+ end
94
+ end
95
+ end
96
+
97
+ private
98
+
99
+ # Get the transaction name based on the operation type and name if possible, or fall back to a user provided
100
+ # one. Useful for anonymous queries.
101
+ def transaction_name(query)
102
+ selected_op = query.selected_operation
103
+ txn_name = if selected_op
104
+ op_type = selected_op.operation_type
105
+ op_name = selected_op.name || fallback_transaction_name(query.context) || "anonymous"
106
+ "#{op_type}.#{op_name}"
107
+ else
108
+ "query.anonymous"
109
+ end
110
+ "GraphQL/#{txn_name}"
111
+ end
112
+
113
+ def fallback_transaction_name(context)
114
+ context[:tracing_fallback_transaction_name]
115
+ end
116
+ end
117
+ end
118
+ end
@@ -10,6 +10,10 @@ module GraphQL
10
10
  class PlatformTracing
11
11
  class << self
12
12
  attr_accessor :platform_keys
13
+
14
+ def inherited(child_class)
15
+ child_class.platform_keys = self.platform_keys
16
+ end
13
17
  end
14
18
 
15
19
  def initialize(options = {})
@@ -26,25 +30,19 @@ module GraphQL
26
30
  yield
27
31
  end
28
32
  when "execute_field", "execute_field_lazy"
29
- if data[:context]
30
- field = data[:context].field
31
- platform_key = field.metadata[:platform_key]
32
- trace_field = true # implemented with instrumenter
33
+ field = data[:field]
34
+ return_type = field.type.unwrap
35
+ trace_field = if return_type.kind.scalar? || return_type.kind.enum?
36
+ (field.trace.nil? && @trace_scalars) || field.trace
33
37
  else
34
- field = data[:field]
35
- return_type = field.type.unwrap
36
- trace_field = if return_type.kind.scalar? || return_type.kind.enum?
37
- (field.trace.nil? && @trace_scalars) || field.trace
38
- else
39
- true
40
- end
38
+ true
39
+ end
41
40
 
42
- platform_key = if trace_field
43
- context = data.fetch(:query).context
44
- cached_platform_key(context, field) { platform_field_key(data[:owner], field) }
45
- else
46
- nil
47
- end
41
+ platform_key = if trace_field
42
+ context = data.fetch(:query).context
43
+ cached_platform_key(context, field, :field) { platform_field_key(field.owner, field) }
44
+ else
45
+ nil
48
46
  end
49
47
 
50
48
  if platform_key && trace_field
@@ -57,14 +55,14 @@ module GraphQL
57
55
  when "authorized", "authorized_lazy"
58
56
  type = data.fetch(:type)
59
57
  context = data.fetch(:context)
60
- platform_key = cached_platform_key(context, type) { platform_authorized_key(type) }
58
+ platform_key = cached_platform_key(context, type, :authorized) { platform_authorized_key(type) }
61
59
  platform_trace(platform_key, key, data) do
62
60
  yield
63
61
  end
64
62
  when "resolve_type", "resolve_type_lazy"
65
63
  type = data.fetch(:type)
66
64
  context = data.fetch(:context)
67
- platform_key = cached_platform_key(context, type) { platform_resolve_type_key(type) }
65
+ platform_key = cached_platform_key(context, type, :resolve_type) { platform_resolve_type_key(type) }
68
66
  platform_trace(platform_key, key, data) do
69
67
  yield
70
68
  end
@@ -74,47 +72,43 @@ module GraphQL
74
72
  end
75
73
  end
76
74
 
77
- def instrument(type, field)
78
- return_type = field.type.unwrap
79
- case return_type
80
- when GraphQL::ScalarType, GraphQL::EnumType
81
- if field.trace || (field.trace.nil? && @trace_scalars)
82
- trace_field(type, field)
75
+ def self.use(schema_defn, options = {})
76
+ if options[:legacy_tracing]
77
+ tracer = self.new(**options)
78
+ schema_defn.tracer(tracer)
79
+ else
80
+ tracing_name = self.name.split("::").last
81
+ trace_name = tracing_name.sub("Tracing", "Trace")
82
+ if GraphQL::Tracing.const_defined?(trace_name, false)
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")
85
+ schema_defn.trace_with(trace_module, **options)
83
86
  else
84
- field
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!")
88
+ tracer = self.new(**options)
89
+ schema_defn.tracer(tracer, silence_deprecation_warning: true)
85
90
  end
86
- else
87
- trace_field(type, field)
88
91
  end
89
92
  end
90
93
 
91
- def trace_field(type, field)
92
- new_f = field.redefine
93
- new_f.metadata[:platform_key] = platform_field_key(type, field)
94
- new_f
95
- end
96
-
97
- def self.use(schema_defn, options = {})
98
- tracer = self.new(**options)
99
- if !schema_defn.is_a?(Class)
100
- schema_defn.instrument(:field, tracer)
101
- end
102
- schema_defn.tracer(tracer)
103
- end
104
-
105
94
  private
106
95
 
107
- # Get the transaction name based on the operation type and name
96
+ # Get the transaction name based on the operation type and name if possible, or fall back to a user provided
97
+ # one. Useful for anonymous queries.
108
98
  def transaction_name(query)
109
99
  selected_op = query.selected_operation
110
- if selected_op
100
+ txn_name = if selected_op
111
101
  op_type = selected_op.operation_type
112
- op_name = selected_op.name || "anonymous"
102
+ op_name = selected_op.name || fallback_transaction_name(query.context) || "anonymous"
103
+ "#{op_type}.#{op_name}"
113
104
  else
114
- op_type = "query"
115
- op_name = "anonymous"
105
+ "query.anonymous"
116
106
  end
117
- "GraphQL/#{op_type}.#{op_name}"
107
+ "GraphQL/#{txn_name}"
108
+ end
109
+
110
+ def fallback_transaction_name(context)
111
+ context[:tracing_fallback_transaction_name]
118
112
  end
119
113
 
120
114
  attr_reader :options
@@ -129,8 +123,11 @@ module GraphQL
129
123
  #
130
124
  # If the key isn't present, the given block is called and the result is cached for `key`.
131
125
  #
126
+ # @param ctx [GraphQL::Query::Context]
127
+ # @param key [Class, GraphQL::Field] A part of the schema
128
+ # @param trace_phase [Symbol] The stage of execution being traced (used by OpenTelementry tracing)
132
129
  # @return [String]
133
- def cached_platform_key(ctx, key)
130
+ def cached_platform_key(ctx, key, trace_phase)
134
131
  cache = ctx.namespace(self.class)[:platform_key_cache] ||= {}
135
132
  cache.fetch(key) { cache[key] = yield }
136
133
  end
@@ -1,11 +1,13 @@
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
- @graphql_gauge = PrometheusExporter::Metric::Summary.new(
10
+ @graphql_gauge = PrometheusExporter::Metric::Base.default_aggregation.new(
9
11
  'graphql_duration_seconds',
10
12
  'Time spent in GraphQL operations, in seconds'
11
13
  )
@@ -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