graphql 2.5.14 → 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 (77) hide show
  1. checksums.yaml +4 -4
  2. data/lib/generators/graphql/detailed_trace_generator.rb +77 -0
  3. data/lib/generators/graphql/templates/create_graphql_detailed_traces.erb +10 -0
  4. data/lib/graphql/dashboard/application_controller.rb +41 -0
  5. data/lib/graphql/dashboard/landings_controller.rb +9 -0
  6. data/lib/graphql/dashboard/statics_controller.rb +31 -0
  7. data/lib/graphql/dashboard/subscriptions.rb +2 -1
  8. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/_form.html.erb +1 -0
  9. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/edit.html.erb +2 -2
  10. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/index.html.erb +1 -1
  11. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/clients/new.html.erb +1 -1
  12. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/index_entries/index.html.erb +1 -1
  13. data/lib/graphql/dashboard/views/graphql/dashboard/operation_store/operations/show.html.erb +1 -1
  14. data/lib/graphql/dashboard/views/graphql/dashboard/subscriptions/topics/show.html.erb +1 -1
  15. data/lib/graphql/dashboard/views/layouts/graphql/dashboard/application.html.erb +7 -7
  16. data/lib/graphql/dashboard.rb +11 -73
  17. data/lib/graphql/dataloader/null_dataloader.rb +7 -3
  18. data/lib/graphql/date_encoding_error.rb +1 -1
  19. data/lib/graphql/execution/interpreter.rb +0 -1
  20. data/lib/graphql/execution/multiplex.rb +1 -1
  21. data/lib/graphql/execution/next/field_resolve_step.rb +711 -0
  22. data/lib/graphql/execution/next/load_argument_step.rb +60 -0
  23. data/lib/graphql/execution/next/prepare_object_step.rb +129 -0
  24. data/lib/graphql/execution/next/runner.rb +389 -0
  25. data/lib/graphql/execution/next/selections_step.rb +37 -0
  26. data/lib/graphql/execution/next.rb +70 -0
  27. data/lib/graphql/execution.rb +1 -0
  28. data/lib/graphql/execution_error.rb +13 -10
  29. data/lib/graphql/introspection/directive_type.rb +7 -3
  30. data/lib/graphql/introspection/dynamic_fields.rb +5 -1
  31. data/lib/graphql/introspection/entry_points.rb +11 -3
  32. data/lib/graphql/introspection/enum_value_type.rb +5 -5
  33. data/lib/graphql/introspection/field_type.rb +13 -5
  34. data/lib/graphql/introspection/input_value_type.rb +21 -13
  35. data/lib/graphql/introspection/type_type.rb +64 -28
  36. data/lib/graphql/invalid_null_error.rb +11 -5
  37. data/lib/graphql/language/document_from_schema_definition.rb +2 -1
  38. data/lib/graphql/language.rb +21 -12
  39. data/lib/graphql/pagination/connection.rb +2 -0
  40. data/lib/graphql/pagination/connections.rb +32 -0
  41. data/lib/graphql/query/context.rb +3 -2
  42. data/lib/graphql/query/null_context.rb +9 -3
  43. data/lib/graphql/schema/argument.rb +12 -0
  44. data/lib/graphql/schema/build_from_definition.rb +7 -0
  45. data/lib/graphql/schema/directive.rb +8 -1
  46. data/lib/graphql/schema/field/connection_extension.rb +15 -35
  47. data/lib/graphql/schema/field/scope_extension.rb +22 -13
  48. data/lib/graphql/schema/field.rb +80 -48
  49. data/lib/graphql/schema/field_extension.rb +33 -0
  50. data/lib/graphql/schema/member/base_dsl_methods.rb +1 -1
  51. data/lib/graphql/schema/member/has_arguments.rb +37 -14
  52. data/lib/graphql/schema/member/has_authorization.rb +35 -0
  53. data/lib/graphql/schema/member/has_dataloader.rb +37 -0
  54. data/lib/graphql/schema/member/has_fields.rb +81 -4
  55. data/lib/graphql/schema/member.rb +5 -0
  56. data/lib/graphql/schema/object.rb +1 -0
  57. data/lib/graphql/schema/resolver.rb +45 -1
  58. data/lib/graphql/schema/validator/required_validator.rb +33 -2
  59. data/lib/graphql/schema/visibility.rb +3 -3
  60. data/lib/graphql/schema.rb +53 -10
  61. data/lib/graphql/static_validation/rules/fields_have_appropriate_selections.rb +2 -2
  62. data/lib/graphql/subscriptions/action_cable_subscriptions.rb +1 -0
  63. data/lib/graphql/subscriptions.rb +1 -1
  64. data/lib/graphql/testing/mock_action_cable.rb +111 -0
  65. data/lib/graphql/testing.rb +1 -0
  66. data/lib/graphql/tracing/detailed_trace/active_record_backend.rb +74 -0
  67. data/lib/graphql/tracing/detailed_trace.rb +70 -7
  68. data/lib/graphql/tracing/perfetto_trace.rb +208 -78
  69. data/lib/graphql/types/relay/connection_behaviors.rb +8 -6
  70. data/lib/graphql/types/relay/edge_behaviors.rb +4 -3
  71. data/lib/graphql/types/relay/has_node_field.rb +13 -8
  72. data/lib/graphql/types/relay/has_nodes_field.rb +13 -8
  73. data/lib/graphql/types/relay/node_behaviors.rb +13 -2
  74. data/lib/graphql/unauthorized_error.rb +5 -1
  75. data/lib/graphql/version.rb +1 -1
  76. data/lib/graphql.rb +8 -2
  77. metadata +17 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: deb0ac3bea401c53909c6880f133ee810f3e0882c7a023ed33b27f7b12a4c82b
4
- data.tar.gz: be2d8e55d131a62863d4ecf6665c22c9ba6c9ba467bdd205ec83d96f9b952098
3
+ metadata.gz: 453860aab49f87d8b8771b00cc50b34a4567e7c80d7ce15b95c1b4fa82b23286
4
+ data.tar.gz: f33d534cbbccfcfb89ba8e6f553ea17d71199ca3fc898ab75c5f3ace08aba820
5
5
  SHA512:
6
- metadata.gz: 494296336070a677965ceaaad1e14412f1b8a6589ab3ae3466c5c00071a59f763f2af2df8aacd394c9fd912afd0a5f9df988991411213dbfab285d762d1a6e75
7
- data.tar.gz: 8d65056236ddb32eabe498d93bb026f8d7ea145b627d6a4554b2add2d8c00db202f9bbe16cae816e58aeb6dd77f3e8aed99dcaa802af2643f73b03a5d10b0b63
6
+ metadata.gz: 3c2c8b87e60b9312ce5fb3848cb9a8112b6d050b6ee9c31eee5720932a2cf754f97f6f7bef273b491199aaa46c7551348e07294270585e79a1e35d176126bdfb
7
+ data.tar.gz: b679a8434d195d513f97963b2fe70b296cb2106ceda4ae2b7c756d1127d8ee4c56f2e3106b4a01c609498904622ada5d569f489bf97a13f8627e7b6a6a1d83fd
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+ require 'rails/generators/active_record'
3
+
4
+ module Graphql
5
+ module Generators
6
+ class DetailedTraceGenerator < ::Rails::Generators::Base
7
+ include ::Rails::Generators::Migration
8
+ desc "Install GraphQL::Tracing::DetailedTrace for your schema"
9
+ source_root File.expand_path('../templates', __FILE__)
10
+
11
+ class_option :redis,
12
+ type: :boolean,
13
+ default: false,
14
+ desc: "Use Redis for persistence instead of ActiveRecord"
15
+
16
+ def self.next_migration_number(dirname)
17
+ ::ActiveRecord::Generators::Base.next_migration_number(dirname)
18
+ end
19
+
20
+ def install_detailed_traces
21
+
22
+ schema_glob = File.expand_path("app/graphql/*_schema.rb", destination_root)
23
+ schema_file = Dir.glob(schema_glob).first
24
+ if !schema_file
25
+ raise ArgumentError, "Failed to find schema definition file (checked: #{schema_glob.inspect})"
26
+ end
27
+ schema_file_match = /( *)class ([A-Za-z:]+) < GraphQL::Schema/.match(File.read(schema_file))
28
+ schema_name = schema_file_match[2]
29
+ indent = schema_file_match[1] + " "
30
+
31
+ if !options.redis?
32
+ migration_template 'create_graphql_detailed_traces.erb', 'db/migrate/create_graphql_detailed_traces.rb'
33
+ end
34
+
35
+ log :add_detailed_traces_plugin
36
+ sentinel = /< GraphQL::Schema\s*\n/m
37
+ code = <<-RUBY
38
+ #{indent}use GraphQL::Tracing::DetailedTrace#{options.redis? ? ", redis: raise(\"TODO: pass a connection to a persistent redis database\")" : ""}, limit: 50
39
+
40
+ #{indent}# When this returns true, DetailedTrace will trace the query
41
+ #{indent}# Could use `query.context`, `query.selected_operation_name`, `query.query_string` here
42
+ #{indent}# Could call out to Flipper, etc
43
+ #{indent}def self.detailed_trace?(query)
44
+ #{indent} rand <= 0.000_1 # one in ten thousand
45
+ #{indent}end
46
+
47
+ RUBY
48
+
49
+ in_root do
50
+ inject_into_file schema_file, code, after: sentinel, force: false
51
+ end
52
+
53
+ routes_source = File.read(File.expand_path("config/routes.rb", destination_root))
54
+ already_has_dashboard = routes_source.include?("GraphQL::Dashboard") ||
55
+ routes_source.include?("Schema.dashboard") ||
56
+ routes_source.include?("GraphQL::Pro::Routes::Lazy")
57
+
58
+ if (!already_has_dashboard || behavior == :revoke)
59
+ log :route, "GraphQL::Dashboard"
60
+ shell.mute do
61
+ route <<~RUBY
62
+ # TODO: add authorization to this route and expose it in production
63
+ # See https://graphql-ruby.org/pro/dashboard.html#authorizing-the-dashboard
64
+ if Rails.env.development?
65
+ mount GraphQL::Dashboard, at: "/graphql/dashboard", schema: #{schema_name.inspect}
66
+ end
67
+
68
+ RUBY
69
+ end
70
+
71
+ gem("google-protobuf")
72
+
73
+ end
74
+ end
75
+ end
76
+ end
77
+ end
@@ -0,0 +1,10 @@
1
+ class CreateGraphqlDetailedTraces < ActiveRecord::Migration[<%= ActiveRecord::Migration.current_version %>]
2
+ def change
3
+ create_table :graphql_detailed_traces, force: true do |t|
4
+ t.bigint :begin_ms, null: false
5
+ t.float :duration_ms, null: false
6
+ t.binary :trace_data, null: false
7
+ t.string :operation_name, null: false
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,41 @@
1
+ # frozen_string_literal: true
2
+ require "action_controller"
3
+
4
+ module Graphql
5
+ class Dashboard < Rails::Engine
6
+ class ApplicationController < ActionController::Base
7
+ protect_from_forgery with: :exception
8
+ prepend_view_path(File.expand_path("../views", __FILE__))
9
+
10
+ content_security_policy do |policy|
11
+ policy.default_src(:self) if policy.default_src(*policy.default_src).blank?
12
+ policy.connect_src(:self) if policy.connect_src(*policy.connect_src).blank?
13
+ policy.base_uri(:none) if policy.base_uri(*policy.base_uri).blank?
14
+ policy.font_src(:self) if policy.font_src(*policy.font_src).blank?
15
+ policy.img_src(:self, :data) if policy.img_src(*policy.img_src).blank?
16
+ policy.object_src(:none) if policy.object_src(*policy.object_src).blank?
17
+ policy.script_src(:self) if policy.script_src(*policy.script_src).blank?
18
+ policy.style_src(:self) if policy.style_src(*policy.style_src).blank?
19
+ policy.form_action(:self) if policy.form_action(*policy.form_action).blank?
20
+ policy.frame_ancestors(:none) if policy.frame_ancestors(*policy.frame_ancestors).blank?
21
+ end
22
+
23
+ def schema_class
24
+ @schema_class ||= begin
25
+ schema_param = request.query_parameters["schema"] || params[:schema]
26
+ case schema_param
27
+ when Class
28
+ schema_param
29
+ when String
30
+ schema_param.constantize
31
+ else
32
+ raise "Missing `params[:schema]`, please provide a class or string to `mount GraphQL::Dashboard, schema: ...`"
33
+ end
34
+ end
35
+ end
36
+ helper_method :schema_class
37
+ end
38
+ end
39
+ end
40
+
41
+ ActiveSupport.run_load_hooks(:graphql_dashboard_application_controller, GraphQL::Dashboard::ApplicationController)
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+ module Graphql
3
+ class Dashboard < Rails::Engine
4
+ class LandingsController < ApplicationController
5
+ def show
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+ module Graphql
3
+ class Dashboard < Rails::Engine
4
+ class StaticsController < ApplicationController
5
+ skip_forgery_protection
6
+ # Use an explicit list of files to avoid any chance of reading other files from disk
7
+ STATICS = {}
8
+
9
+ [
10
+ "icon.png",
11
+ "header-icon.png",
12
+ "charts.min.css",
13
+ "dashboard.css",
14
+ "dashboard.js",
15
+ "bootstrap-5.3.3.min.css",
16
+ "bootstrap-5.3.3.min.js",
17
+ ].each do |static_file|
18
+ STATICS[static_file] = File.expand_path("../statics/#{static_file}", __FILE__)
19
+ end
20
+
21
+ def show
22
+ expires_in 1.year, public: true
23
+ if (filepath = STATICS[params[:id]])
24
+ render file: filepath
25
+ else
26
+ head :not_found
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+ require_relative "./installable"
2
3
  module Graphql
3
4
  class Dashboard < Rails::Engine
4
5
  module Subscriptions
@@ -6,7 +7,7 @@ module Graphql
6
7
  include Installable
7
8
 
8
9
  def feature_installed?
9
- schema_class.subscriptions.is_a?(GraphQL::Pro::Subscriptions)
10
+ defined?(GraphQL::Pro::Subscriptions) && schema_class.subscriptions.is_a?(GraphQL::Pro::Subscriptions)
10
11
  end
11
12
 
12
13
  INSTALLABLE_COMPONENT_HEADER_HTML = "GraphQL-Pro Subscriptions aren't installed on this schema yet.".html_safe
@@ -20,4 +20,5 @@
20
20
  <div class="col-auto">
21
21
  <%= link_to "Back", graphql_dashboard.operation_store_clients_path, class: "btn btn-outline-secondary" %>
22
22
  </div>
23
+ </div>
23
24
  <% end %>
@@ -3,10 +3,10 @@
3
3
  <div class="col">
4
4
  <h1>Edit <%= @client.name %></h1>
5
5
  </div>
6
- <div>
6
+ </div>
7
7
  <%= render partial: "graphql/dashboard/operation_store/clients/form" %>
8
8
 
9
- <hr class="mt-5"/>
9
+ <hr class="mt-5">
10
10
  <div class="row mt-5">
11
11
  <div class="col">
12
12
  <div class="alert alert-danger">
@@ -33,7 +33,7 @@
33
33
  <td><%= link_to(client.name, graphql_dashboard.edit_operation_store_client_path(name: client.name)) %></td>
34
34
  <td>
35
35
  <%= link_to(graphql_dashboard.operation_store_client_operations_path(client_name: client.name)) do %>
36
- <%= client.operations_count %><% if client.archived_operations_count > 0 %> <span class="muted">(<%=client.archived_operations_count%> archived)</span><% end %>
36
+ <%= client.operations_count %><% if client.archived_operations_count > 0 %> <span class="muted">(<%= client.archived_operations_count %> archived)</span><% end %>
37
37
  <% end %>
38
38
  </td>
39
39
  <td><%= client.created_at %></td>
@@ -3,5 +3,5 @@
3
3
  <div class="col">
4
4
  <h1>New Client</h1>
5
5
  </div>
6
- <div>
6
+ </div>
7
7
  <%= render partial: "graphql/dashboard/operation_store/clients/form" %>
@@ -10,7 +10,7 @@
10
10
  <form method="GET" action="<%= graphql_dashboard.operation_store_index_entries_path %>" style="margin-left: auto; margin-top:-5px;">
11
11
  <div class="input-group">
12
12
  <%= text_field_tag "q", @search_term, class: "form-control", placeholder: "Find types, fields, arguments, or enum values" %>
13
- <input type="submit" value="Search" class="btn btn-outline-primary btn-sm"/>
13
+ <input type="submit" value="Search" class="btn btn-outline-primary btn-sm">
14
14
  </div>
15
15
  </form>
16
16
  </div>
@@ -2,7 +2,7 @@
2
2
  <% if @operation.nil? %>
3
3
  <div class="row">
4
4
  <div class="col">
5
- <p>No stored operation found for <code><%= params[:digest] %></code>
5
+ <p>No stored operation found for <code><%= params[:digest] %></code></p>
6
6
  </div>
7
7
  </div>
8
8
  <% else %>
@@ -9,7 +9,7 @@
9
9
  <div class="col">
10
10
  <p>Last triggered: <%= @topic_last_triggered_at || "none" %></p>
11
11
  <p><%= pluralize(@subscriptions_count, "Subscription") %></p>
12
- <div>
12
+ </div>
13
13
  </div>
14
14
 
15
15
  <div class="row">
@@ -1,15 +1,15 @@
1
1
  <!doctype html>
2
2
  <html lang="en" class="h-100" >
3
3
  <head>
4
- <link rel="icon" type="image/png" href="<%= graphql_dashboard.static_path("icon.png") %>" />
4
+ <link rel="icon" type="image/png" href="<%= graphql_dashboard.static_path("icon.png") %>">
5
5
  <meta charset="utf-8">
6
6
  <meta name="viewport" content="width=device-width, initial-scale=1">
7
7
  <title>GraphQL Dashboard <%= content_for?(:title) ? " · #{content_for(:title)}" : "" %> </title>
8
- <%= stylesheet_link_tag graphql_dashboard.static_path("bootstrap-5.3.3.min.css") %>
9
- <%= stylesheet_link_tag graphql_dashboard.static_path("charts.min.css") %>
10
- <%= stylesheet_link_tag graphql_dashboard.static_path("dashboard.css") %>
11
- <%= javascript_include_tag graphql_dashboard.static_path("bootstrap-5.3.3.min.js") %>
12
- <%= javascript_include_tag graphql_dashboard.static_path("dashboard.js") %>
8
+ <link rel="stylesheet" href="<%= graphql_dashboard.static_path("bootstrap-5.3.3.min.css") %>" media="screen">
9
+ <link rel="stylesheet" href="<%= graphql_dashboard.static_path("charts.min.css") %>" media="screen">
10
+ <link rel="stylesheet" href="<%= graphql_dashboard.static_path("dashboard.css") %>" media="screen">
11
+ <script src="<%= graphql_dashboard.static_path("bootstrap-5.3.3.min.js") %>"></script>
12
+ <script src="<%= graphql_dashboard.static_path("dashboard.js") %>"></script>
13
13
  <%= csrf_meta_tags %>
14
14
  </head>
15
15
  <body class="h-100 d-flex flex-column">
@@ -20,7 +20,7 @@
20
20
  <nav class="navbar navbar-expand-lg bg-body-tertiary">
21
21
  <div class="container-fluid">
22
22
  <%= link_to graphql_dashboard.root_path, class: "navbar-brand" do %>
23
- <img id="header-icon" src="<%= graphql_dashboard.static_path("header-icon.png") %>" alt="GraphQL-Ruby" />
23
+ <img id="header-icon" src="<%= graphql_dashboard.static_path("header-icon.png") %>" alt="GraphQL-Ruby">
24
24
  <% end %>
25
25
  <button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
26
26
  <span class="navbar-toggler-icon"></span>
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
  require 'rails/engine'
3
+ require 'action_controller'
3
4
  module Graphql
4
5
  # `GraphQL::Dashboard` is a `Rails::Engine`-based dashboard for viewing metadata about your GraphQL schema.
5
6
  #
@@ -34,7 +35,16 @@ module Graphql
34
35
  class Dashboard < Rails::Engine
35
36
  engine_name "graphql_dashboard"
36
37
  isolate_namespace(Graphql::Dashboard)
37
- routes.draw do
38
+
39
+ autoload :ApplicationController, "graphql/dashboard/application_controller"
40
+ autoload :LandingsController, "graphql/dashboard/landings_controller"
41
+ autoload :StaticsController, "graphql/dashboard/statics_controller"
42
+ autoload :DetailedTraces, "graphql/dashboard/detailed_traces"
43
+ autoload :Subscriptions, "graphql/dashboard/subscriptions"
44
+ autoload :OperationStore, "graphql/dashboard/operation_store"
45
+ autoload :Limiters, "graphql/dashboard/limiters"
46
+
47
+ routes do
38
48
  root "landings#show"
39
49
  resources :statics, only: :show, constraints: { id: /[0-9A-Za-z\-.]+/ }
40
50
 
@@ -77,82 +87,10 @@ module Graphql
77
87
  post "/subscriptions/clear_all", to: "subscriptions#clear_all", as: :clear_all
78
88
  end
79
89
  end
80
-
81
- class ApplicationController < ActionController::Base
82
- protect_from_forgery with: :exception
83
- prepend_view_path(File.join(__FILE__, "../dashboard/views"))
84
-
85
- content_security_policy do |policy|
86
- policy.default_src(:self) if policy.default_src(*policy.default_src).blank?
87
- policy.connect_src(:self) if policy.connect_src(*policy.connect_src).blank?
88
- policy.base_uri(:none) if policy.base_uri(*policy.base_uri).blank?
89
- policy.font_src(:self) if policy.font_src(*policy.font_src).blank?
90
- policy.img_src(:self, :data) if policy.img_src(*policy.img_src).blank?
91
- policy.object_src(:none) if policy.object_src(*policy.object_src).blank?
92
- policy.script_src(:self) if policy.script_src(*policy.script_src).blank?
93
- policy.style_src(:self) if policy.style_src(*policy.style_src).blank?
94
- policy.form_action(:self) if policy.form_action(*policy.form_action).blank?
95
- policy.frame_ancestors(:none) if policy.frame_ancestors(*policy.frame_ancestors).blank?
96
- end
97
-
98
- def schema_class
99
- @schema_class ||= begin
100
- schema_param = request.query_parameters["schema"] || params[:schema]
101
- case schema_param
102
- when Class
103
- schema_param
104
- when String
105
- schema_param.constantize
106
- else
107
- raise "Missing `params[:schema]`, please provide a class or string to `mount GraphQL::Dashboard, schema: ...`"
108
- end
109
- end
110
- end
111
- helper_method :schema_class
112
- end
113
-
114
- class LandingsController < ApplicationController
115
- def show
116
- end
117
- end
118
-
119
- class StaticsController < ApplicationController
120
- skip_after_action :verify_same_origin_request
121
- # Use an explicit list of files to avoid any chance of reading other files from disk
122
- STATICS = {}
123
-
124
- [
125
- "icon.png",
126
- "header-icon.png",
127
- "charts.min.css",
128
- "dashboard.css",
129
- "dashboard.js",
130
- "bootstrap-5.3.3.min.css",
131
- "bootstrap-5.3.3.min.js",
132
- ].each do |static_file|
133
- STATICS[static_file] = File.expand_path("../dashboard/statics/#{static_file}", __FILE__)
134
- end
135
-
136
- def show
137
- expires_in 1.year, public: true
138
- if (filepath = STATICS[params[:id]])
139
- render file: filepath
140
- else
141
- head :not_found
142
- end
143
- end
144
- end
145
90
  end
146
91
  end
147
92
 
148
- require 'graphql/dashboard/detailed_traces'
149
- require 'graphql/dashboard/limiters'
150
- require 'graphql/dashboard/operation_store'
151
- require 'graphql/dashboard/subscriptions'
152
-
153
93
  # Rails expects the engine to be called `Graphql::Dashboard`,
154
94
  # but `GraphQL::Dashboard` is consistent with this gem's naming.
155
95
  # So define both constants to refer to the same class.
156
96
  GraphQL::Dashboard = Graphql::Dashboard
157
-
158
- ActiveSupport.run_load_hooks(:graphql_dashboard_application_controller, GraphQL::Dashboard::ApplicationController)
@@ -37,13 +37,17 @@ module GraphQL
37
37
  end
38
38
 
39
39
  def run_isolated
40
- new_dl = self.class.new
40
+ # Reuse this instance because execution code may already have a reference to _this_ `dataloader` inside the given block.
41
+ prev_lazies_at_depth = @lazies_at_depth
42
+ @lazies_at_depth = @lazies_at_depth.dup.clear
41
43
  res = nil
42
- new_dl.append_job {
44
+ append_job {
43
45
  res = yield
44
46
  }
45
- new_dl.run
47
+ run
46
48
  res
49
+ ensure
50
+ @lazies_at_depth = prev_lazies_at_depth
47
51
  end
48
52
 
49
53
  def clear_cache; end
@@ -10,7 +10,7 @@ module GraphQL
10
10
 
11
11
  def initialize(value)
12
12
  @date_value = value
13
- super("Date cannot be parsed: #{value}. \nDate must be be able to be parsed as a Ruby Date object.")
13
+ super("Date cannot be parsed: #{value}. \nDate must be able to be parsed as a Ruby Date object.")
14
14
  end
15
15
  end
16
16
  end
@@ -80,7 +80,6 @@ module GraphQL
80
80
  end
81
81
  rescue GraphQL::ExecutionError => err
82
82
  query.context.errors << err
83
- NO_OPERATION
84
83
  end
85
84
  end
86
85
  results[idx] = result
@@ -33,7 +33,7 @@ module GraphQL
33
33
  @queries.each { |q| q.multiplex = self }
34
34
  @context = context
35
35
  @dataloader = @context[:dataloader] ||= @schema.dataloader_class.new
36
- @tracers = schema.tracers + (context[:tracers] || [])
36
+ @tracers = schema.tracers + (context[:tracers] || EmptyObjects::EMPTY_ARRAY)
37
37
  @max_complexity = max_complexity
38
38
  @current_trace = context[:trace] ||= schema.new_trace(multiplex: self)
39
39
  @logger = nil