graphql-persisted_queries 1.0.2 → 1.2.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (35) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/rspec.yml +53 -0
  3. data/.github/workflows/rubocop.yml +21 -0
  4. data/CHANGELOG.md +24 -2
  5. data/README.md +25 -14
  6. data/Rakefile +29 -1
  7. data/benchmark/compiled_queries.rb +41 -0
  8. data/benchmark/helpers.rb +31 -0
  9. data/benchmark/persisted_queries.rb +41 -0
  10. data/benchmark/plain_gql.rb +33 -0
  11. data/docs/compiled_queries_benchmark.md +75 -0
  12. data/gemfiles/{graphql_1_8.gemfile → graphql_1_11.gemfile} +1 -1
  13. data/gemfiles/{graphql_1_9.gemfile → graphql_1_12_0.gemfile} +1 -1
  14. data/gemfiles/graphql_1_12_4.gemfile +5 -0
  15. data/graphql-persisted_queries.gemspec +1 -1
  16. data/lib/graphql/persisted_queries.rb +26 -3
  17. data/lib/graphql/persisted_queries/compiled_queries/multiplex_patch.rb +30 -0
  18. data/lib/graphql/persisted_queries/compiled_queries/query_patch.rb +33 -0
  19. data/lib/graphql/persisted_queries/compiled_queries/resolver.rb +38 -0
  20. data/lib/graphql/persisted_queries/error_handlers.rb +4 -4
  21. data/lib/graphql/persisted_queries/error_handlers/base_error_handler.rb +1 -1
  22. data/lib/graphql/persisted_queries/errors.rb +19 -0
  23. data/lib/graphql/persisted_queries/multiplex_resolver.rb +5 -4
  24. data/lib/graphql/persisted_queries/resolver.rb +11 -33
  25. data/lib/graphql/persisted_queries/resolver_helpers.rb +26 -0
  26. data/lib/graphql/persisted_queries/schema_patch.rb +31 -22
  27. data/lib/graphql/persisted_queries/store_adapters.rb +4 -4
  28. data/lib/graphql/persisted_queries/store_adapters/base_store_adapter.rb +15 -5
  29. data/lib/graphql/persisted_queries/store_adapters/memcached_store_adapter.rb +1 -1
  30. data/lib/graphql/persisted_queries/store_adapters/memory_store_adapter.rb +1 -1
  31. data/lib/graphql/persisted_queries/store_adapters/redis_store_adapter.rb +1 -1
  32. data/lib/graphql/persisted_queries/store_adapters/redis_with_local_cache_store_adapter.rb +1 -1
  33. data/lib/graphql/persisted_queries/version.rb +1 -1
  34. metadata +23 -11
  35. data/.travis.yml +0 -24
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: a54ca19186e396ff8a0148b3fc272ed6980dd62e150ca027620d51c105373cb8
4
- data.tar.gz: 5c49f66f61b87648f08259fb93e3f810a656b24fdc4f6ecbcdeed5e2f2b9db8f
3
+ metadata.gz: 51e6b75b3baabc1ace75eab3b689bcbb6ee7082362036d6fc0dc70858f803a04
4
+ data.tar.gz: 4db1546160fd4ca16f9a67899b6e4cbd97140f75afa689e0214d3d7197ee729f
5
5
  SHA512:
6
- metadata.gz: 36d204d8c8874a85c454a0e74884ac750b538cc993ade9e1d70b038e089934012beb515d9aa8d2fc8a5e4ed90c9a7a4e3dce975fef24919271d7472d2e158b77
7
- data.tar.gz: 15f63fca919296e2bdf7624a4eaefd78a05415f17839d6ef5cd56881ba3b8c05e68f9929ccc93b0b503383226607d8dce34a8b11bb9ed99064eabb088f81c3fd
6
+ metadata.gz: aa30f3bddf9c7f933cc62d69199bceb5c55a430e8b3eca8e36c8eb9e1c78bb71f285b1f849b448e81fcb980afa9e5e2c6c4bc34e26041b6a612e830a8e4548a1
7
+ data.tar.gz: c1975bef00a57a1f18c37fde0811c5eb81d5ebfd8bd9704d02f05924e42251aa2c83f3008d7b3f2ba71face9567f39df5a3d4f2cfbbfef61be04c6a610b0942c
@@ -0,0 +1,53 @@
1
+ name: RSpec
2
+
3
+ on:
4
+ push:
5
+ branches: [ master ]
6
+ pull_request:
7
+ branches: [ master ]
8
+ schedule:
9
+ - cron: "0 10 * * *"
10
+
11
+ jobs:
12
+ rspec:
13
+ runs-on: ubuntu-latest
14
+
15
+ env:
16
+ CI: true
17
+
18
+ strategy:
19
+ fail-fast: false
20
+ matrix:
21
+ ruby: [2.3, 2.4, 2.5, 2.6, 2.7]
22
+ gemfile: [
23
+ "gemfiles/graphql_1_10.gemfile",
24
+ "gemfiles/graphql_1_11.gemfile",
25
+ "gemfiles/graphql_1_12_0.gemfile",
26
+ "gemfiles/graphql_1_12_4.gemfile",
27
+ "gemfiles/graphql_master.gemfile"
28
+ ]
29
+
30
+ steps:
31
+ - uses: actions/checkout@v2
32
+ - uses: actions/cache@v2
33
+ with:
34
+ path: /home/runner/bundle
35
+ key: bundle-${{ matrix.ruby }}-${{ matrix.gemfile }}-${{ hashFiles(matrix.gemfile) }}-${{ hashFiles('**/*.gemspec') }}
36
+ restore-keys: |
37
+ bundle-${{ matrix.ruby }}-${{ matrix.gemfile }}-
38
+ - uses: ruby/setup-ruby@v1
39
+ with:
40
+ ruby-version: ${{ matrix.ruby }}
41
+ - name: Install system deps
42
+ run: |
43
+ sudo apt-get update
44
+ sudo apt-get install libsqlite3-dev
45
+ - name: Bundle install
46
+ run: |
47
+ bundle config path /home/runner/bundle
48
+ bundle config --global gemfile ${{ matrix.gemfile }}
49
+ bundle install
50
+ bundle update
51
+ - name: Run RSpec
52
+ run: |
53
+ bundle exec rake ci_specs
@@ -0,0 +1,21 @@
1
+ name: Rubocop
2
+
3
+ on:
4
+ push:
5
+ branches: [ master ]
6
+ pull_request:
7
+ branches: [ master ]
8
+
9
+ jobs:
10
+ rubocop:
11
+ runs-on: ubuntu-latest
12
+
13
+ steps:
14
+ - uses: actions/checkout@v2
15
+ - uses: ruby/setup-ruby@v1
16
+ with:
17
+ ruby-version: 2.7
18
+ - name: Lint Ruby code with RuboCop
19
+ run: |
20
+ bundle install --gemfile gemfiles/graphql_1_10.gemfile --jobs 4 --retry 3
21
+ bundle exec --gemfile gemfiles/graphql_1_10.gemfile rubocop
data/CHANGELOG.md CHANGED
@@ -2,13 +2,34 @@
2
2
 
3
3
  ## master
4
4
 
5
+ ## 1.2.2 (2021-04-21)
6
+
7
+ - [PR#47](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/47) Properly initialize memory adapter inside RedisWithLocalCacheStoreAdapter ([@DmitryTsepelev][])
8
+
9
+ ## 1.2.1 (2021-03-07)
10
+
11
+ - [PR#43](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/43) Properly handle configuration when schema is inherited ([@DmitryTsepelev][])
12
+ - [PR#44](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/44) Deprecate graphql-ruby 1.8 and 1.9 ([@DmitryTsepelev][])
13
+
14
+ ## 1.2.0 (2021-02-24)
15
+
16
+ - [PR#39](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/39) Implement compiled queries ([@DmitryTsepelev][])
17
+
18
+ ## 1.1.1 (2020-12-03)
19
+
20
+ - [PR#37](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/37) Fix deprecation warnings ([@rbviz][])
21
+
22
+ ## 1.1.0 (2020-11-16)
23
+
24
+ - [PR#36](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/36) Support Ruby 2.7.0 ([@DmitryTsepelev][])
25
+
5
26
  ## 1.0.2 (2020-06-29)
6
27
 
7
- - [PR#35](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/35) fix args for GraphQL::Query::Result ([@ogidow ][])
28
+ - [PR#35](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/35) fix args for GraphQL::Query::Result ([@ogidow][])
8
29
 
9
30
  ## 1.0.1 (2020-06-25)
10
31
 
11
- - [PR#34](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/34) Return GraphQL::Query::Result when raise error ([@ogidow ][])
32
+ - [PR#34](https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries/pull/34) Return GraphQL::Query::Result when raise error ([@ogidow][])
12
33
 
13
34
  ## 🥳 1.0.0 (2020-03-31)
14
35
 
@@ -56,3 +77,4 @@
56
77
  [@bmorton]: https://github.com/bmorton
57
78
  [@JanStevens]: https://github.com/JanStevens
58
79
  [@ogidow]: https://github.com/ogidow
80
+ [@rbviz]: https://github.com/rbviz
data/README.md CHANGED
@@ -1,7 +1,6 @@
1
- # GraphQL::PersistedQueries [![Build Status](https://travis-ci.org/DmitryTsepelev/graphql-ruby-persisted_queries.svg?branch=master)](https://travis-ci.org/DmitryTsepelev/graphql-ruby-persisted_queries)
1
+ # GraphQL::PersistedQueries
2
2
 
3
-
4
- `GraphQL::PersistedQueries` is the implementation of [persisted queries](https://github.com/apollographql/apollo-link-persisted-queries) for [graphql-ruby](https://github.com/rmosolgo/graphql-ruby). With this plugin your backend will cache all the queries, while frontend will send the full query only when it's not found at the backend storage.
3
+ `GraphQL::PersistedQueries` is the implementation of [persisted queries](https://www.apollographql.com/docs/react/api/link/persisted-queries/) for [graphql-ruby](https://github.com/rmosolgo/graphql-ruby). With this plugin your backend will cache all the queries, while frontend will send the full query only when it's not found at the backend storage.
5
4
 
6
5
  - 🗑**Heavy query parameter will be omitted in most of cases** – network requests will become less heavy
7
6
  - 🤝**Clients share cached queries** – it's enough to miss cache only once for each unique query
@@ -16,20 +15,18 @@
16
15
 
17
16
  ## Getting started
18
17
 
19
- First of all, install and configure [apollo-link-persisted-queries](https://github.com/apollographql/apollo-link-persisted-queries) on the front–end side:
18
+ First of all, install and configure [apollo's persisted queries](https://www.apollographql.com/docs/react/api/link/persisted-queries/) on the front–end side:
20
19
 
21
20
  ```js
22
- import { createPersistedQueryLink } from "apollo-link-persisted-queries";
23
- import { createHttpLink } from "apollo-link-http";
24
- import { InMemoryCache } from "apollo-cache-inmemory";
25
- import ApolloClient from "apollo-client";
26
-
21
+ import { HttpLink, InMemoryCache, ApolloClient } from "@apollo/client";
22
+ import { createPersistedQueryLink } from "@apollo/client/link/persisted-queries";
23
+ import { sha256 } from 'crypto-hash';
27
24
 
28
- // use this with Apollo Client
29
- const link = createPersistedQueryLink().concat(createHttpLink({ uri: "/graphql" }));
25
+ const httpLink = new HttpLink({ uri: "/graphql" });
26
+ const persistedQueriesLink = createPersistedQueryLink({ sha256 });
30
27
  const client = new ApolloClient({
31
28
  cache: new InMemoryCache(),
32
- link: link,
29
+ link: persistedQueriesLink.concat(httpLink);
33
30
  });
34
31
  ```
35
32
 
@@ -66,6 +63,20 @@ GraphqlSchema.execute(
66
63
 
67
64
  You're all set!
68
65
 
66
+ ## Compiled queries (increases performance up to 2x!)
67
+
68
+ When query arrives to the backend, GraphQL execution engine needs some time to _parse_ it and build the AST. In case of a huge query it might take [a lot](https://gist.github.com/DmitryTsepelev/36e290cf64b4ec0b18294d0a57fb26ff#file-1_result-md) of time. What if we cache the AST instead of a query text and skip parsing completely? The only thing you need to do is to turn `:compiled_queries` option on:
69
+
70
+ ```ruby
71
+ class GraphqlSchema < GraphQL::Schema
72
+ use GraphQL::PersistedQueries, compiled_queries: true
73
+ end
74
+ ```
75
+
76
+ Using this option might make your endpoint up to 2x faster according to the [benchmark](docs/compiled_queries_benchmark.md).
77
+
78
+ **Heads up!** This feature only works on `graphql-ruby` 1.12.0 or later, but I guess it might be backported.
79
+
69
80
  ## Advanced usage
70
81
 
71
82
  All the queries are stored in memory by default, but you can easily switch to another storage (e.g., _redis_:
@@ -82,9 +93,9 @@ When the error occurs, the gem tries to not interrupt the regular flow of the ap
82
93
 
83
94
  Since our queries are slim now, we can switch back to HTTP GET, you can find a [guide](docs/http_cache.md) here.
84
95
 
85
- [batch-link](https://www.apollographql.com/docs/link/links/batch-http/) allows to group queries on the client side into a single HTTP request before sending to the server. In this case you need to use `GraphqlSchema.multiplex(queries)` instead of `#execute`. The gem supports it too, no action required!
96
+ [batch-link](https://www.apollographql.com/docs/react/api/link/apollo-link-batch-http/) allows to group queries on the client side into a single HTTP request before sending to the server. In this case you need to use `GraphqlSchema.multiplex(queries)` instead of `#execute`. The gem supports it too, no action required!
86
97
 
87
- [apollo-link-persisted-queries](https://github.com/apollographql/apollo-link-persisted-queries) uses _SHA256_ for building hashes by default. Check out this [guide](docs/hash.md) if you want to override this behavior.
98
+ [persisted-queries-link](https://www.apollographql.com/docs/react/api/link/persisted-queries/) uses _SHA256_ for building hashes by default. Check out this [guide](docs/hash.md) if you want to override this behavior.
88
99
 
89
100
  An experimental tracing feature can be enabled by setting `tracing: true` when configuring the plugin. Read more about this feature in the [Tracing guide](docs/tracing.md).
90
101
 
data/Rakefile CHANGED
@@ -5,4 +5,32 @@ require "rubocop/rake_task"
5
5
  RSpec::Core::RakeTask.new(:spec)
6
6
  RuboCop::RakeTask.new
7
7
 
8
- task default: [:rubocop, :spec]
8
+ desc "Run specs for compiled queries"
9
+ RSpec::Core::RakeTask.new("spec:compiled_queries") do |task|
10
+ task.pattern = "**/compiled_queries/**"
11
+ task.verbose = false
12
+ end
13
+
14
+ RSpec::Core::RakeTask.new("spec:without_compiled_queries") do |task|
15
+ task.exclude_pattern = "**/compiled_queries/**"
16
+ task.verbose = false
17
+ end
18
+
19
+ task ci_specs: ["spec:without_compiled_queries", "spec:compiled_queries"]
20
+
21
+ task :bench_gql do
22
+ cmd = %w[bundle exec ruby benchmark/plain_gql.rb]
23
+ system(*cmd)
24
+ end
25
+
26
+ task :bench_pq do
27
+ cmd = %w[bundle exec ruby benchmark/persisted_queries.rb]
28
+ system(*cmd)
29
+ end
30
+
31
+ task :bench_compiled do
32
+ cmd = %w[bundle exec ruby benchmark/compiled_queries.rb]
33
+ system(*cmd)
34
+ end
35
+
36
+ task bench: [:bench_gql, :bench_pq, :bench_compiled]
@@ -0,0 +1,41 @@
1
+ require "bundler/inline"
2
+
3
+ gemfile do
4
+ source "https://rubygems.org"
5
+ gem "graphql", "1.12.4"
6
+ end
7
+
8
+ $:.push File.expand_path("../lib", __dir__)
9
+
10
+ require "benchmark"
11
+ require "graphql/persisted_queries"
12
+ require_relative "helpers"
13
+
14
+ class GraphqlSchema < GraphQL::Schema
15
+ use GraphQL::PersistedQueries, compiled_queries: true
16
+
17
+ query QueryType
18
+ end
19
+
20
+ GraphqlSchema.to_definition
21
+
22
+ puts
23
+ puts "Schema with compiled queries:"
24
+ puts
25
+
26
+ Benchmark.bm(28) do |x|
27
+ [false, true].each do |with_nested|
28
+ FIELD_COUNTS.each do |field_count|
29
+ query = generate_query(field_count, with_nested)
30
+ sha256 = Digest::SHA256.hexdigest(query)
31
+
32
+ context = { extensions: { "persistedQuery" => { "sha256Hash" => sha256 } } }
33
+ # warmup
34
+ GraphqlSchema.execute(query, context: context)
35
+
36
+ x.report("#{field_count} fields#{" (nested)" if with_nested}") do
37
+ GraphqlSchema.execute(query, context: context)
38
+ end
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,31 @@
1
+ FIELD_COUNTS = [10, 50, 100, 200, 300]
2
+
3
+ def generate_fields(field_count, with_nested)
4
+ fields = field_count.times.map do |i|
5
+ field = "field#{i+1}"
6
+ field += "\s{#{generate_fields(field_count, false)}}" if with_nested
7
+ field
8
+ end
9
+
10
+ fields.join("\n")
11
+ end
12
+
13
+ def generate_query(field_count, with_nested)
14
+ <<-gql
15
+ query {
16
+ #{generate_fields(field_count, with_nested)}
17
+ }
18
+ gql
19
+ end
20
+
21
+ class ChildType < GraphQL::Schema::Object
22
+ FIELD_COUNTS.max.times do |i|
23
+ field "field#{i + 1}".to_sym, String, null: false, method: :itself
24
+ end
25
+ end
26
+
27
+ class QueryType < GraphQL::Schema::Object
28
+ FIELD_COUNTS.max.times do |i|
29
+ field "field#{i + 1}".to_sym, ChildType, null: false, method: :itself
30
+ end
31
+ end
@@ -0,0 +1,41 @@
1
+ require "bundler/inline"
2
+
3
+ gemfile do
4
+ source "https://rubygems.org"
5
+ gem "graphql", "1.12.4"
6
+ end
7
+
8
+ $:.push File.expand_path("../lib", __dir__)
9
+
10
+ require "benchmark"
11
+ require "graphql/persisted_queries"
12
+ require_relative "helpers"
13
+
14
+ class GraphqlSchema < GraphQL::Schema
15
+ use GraphQL::PersistedQueries
16
+
17
+ query QueryType
18
+ end
19
+
20
+ GraphqlSchema.to_definition
21
+
22
+ puts
23
+ puts "Schema with persisted queries:"
24
+ puts
25
+
26
+ Benchmark.bm(28) do |x|
27
+ [false, true].each do |with_nested|
28
+ FIELD_COUNTS.each do |field_count|
29
+ query = generate_query(field_count, with_nested)
30
+ sha256 = Digest::SHA256.hexdigest(query)
31
+ context = { extensions: { "persistedQuery" => { "sha256Hash" => sha256 } } }
32
+
33
+ # warmup
34
+ GraphqlSchema.execute(query, context: context)
35
+
36
+ x.report("#{field_count} fields#{" (nested)" if with_nested}") do
37
+ GraphqlSchema.execute(query, context: context)
38
+ end
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,33 @@
1
+ require "bundler/inline"
2
+
3
+ gemfile do
4
+ source "https://rubygems.org"
5
+ gem "graphql", "1.12.4"
6
+ end
7
+
8
+ $:.push File.expand_path("../lib", __dir__)
9
+
10
+ require "benchmark"
11
+ require "graphql/persisted_queries"
12
+ require_relative "helpers"
13
+
14
+ class GraphqlSchema < GraphQL::Schema
15
+ query QueryType
16
+ end
17
+
18
+ GraphqlSchema.to_definition
19
+
20
+ puts "Plain schema:"
21
+ puts
22
+
23
+ Benchmark.bm(28) do |x|
24
+ [false, true].each do |with_nested|
25
+ FIELD_COUNTS.each do |field_count|
26
+ query = generate_query(field_count, with_nested)
27
+
28
+ x.report("#{field_count} fields#{" (nested)" if with_nested}") do
29
+ GraphqlSchema.execute(query)
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,75 @@
1
+ # Compiled queries benchmarks
2
+
3
+ The name of benchmark consists of a field count and optional "nested" label. In case of non–nested one we just generate a query with that field count, e.g. `2 fields` means:
4
+
5
+ ```gql
6
+ query {
7
+ field1
8
+ field2
9
+ }
10
+ ```
11
+
12
+ In case of "nested" benchmark we also put a list of fields to each top–level field, e.g. `2 fields (nested)` means:
13
+
14
+ ```gql
15
+ query {
16
+ field1 {
17
+ field1
18
+ field2
19
+ }
20
+ field2 {
21
+ field1
22
+ field2
23
+ }
24
+ }
25
+ ```
26
+
27
+ Field resolver just returns a string, so real–world tests might be way slower because of IO.
28
+
29
+ Here are the results:
30
+
31
+ ```
32
+ Plain schema:
33
+
34
+ user system total real
35
+ 10 fields 0.001061 0.000039 0.001100 ( 0.001114)
36
+ 50 fields 0.001658 0.000003 0.001661 ( 0.001661)
37
+ 100 fields 0.004587 0.000026 0.004613 ( 0.004614)
38
+ 200 fields 0.006447 0.000016 0.006463 ( 0.006476)
39
+ 300 fields 0.024493 0.000073 0.024566 ( 0.024614)
40
+ 10 fields (nested) 0.003061 0.000043 0.003104 ( 0.003109)
41
+ 50 fields (nested) 0.056927 0.000995 0.057922 ( 0.057997)
42
+ 100 fields (nested) 0.245235 0.001336 0.246571 ( 0.246727)
43
+ 200 fields (nested) 0.974444 0.006531 0.980975 ( 0.981810)
44
+ 300 fields (nested) 2.175855 0.012773 2.188628 ( 2.190130)
45
+
46
+ Schema with persisted queries:
47
+
48
+ user system total real
49
+ 10 fields 0.000606 0.000007 0.000613 ( 0.000607)
50
+ 50 fields 0.001855 0.000070 0.001925 ( 0.001915)
51
+ 100 fields 0.003239 0.000009 0.003248 ( 0.003239)
52
+ 200 fields 0.007542 0.000009 0.007551 ( 0.007551)
53
+ 300 fields 0.014975 0.000237 0.015212 ( 0.015318)
54
+ 10 fields (nested) 0.002992 0.000068 0.003060 ( 0.003049)
55
+ 50 fields (nested) 0.062314 0.000274 0.062588 ( 0.062662)
56
+ 100 fields (nested) 0.256404 0.000865 0.257269 ( 0.257419)
57
+ 200 fields (nested) 0.978408 0.007437 0.985845 ( 0.986579)
58
+ 300 fields (nested) 2.263338 0.010994 2.274332 ( 2.275967)
59
+
60
+ Schema with compiled queries:
61
+
62
+ user system total real
63
+ 10 fields 0.000526 0.000009 0.000535 ( 0.000530)
64
+ 50 fields 0.001280 0.000012 0.001292 ( 0.001280)
65
+ 100 fields 0.002292 0.000004 0.002296 ( 0.002286)
66
+ 200 fields 0.005462 0.000001 0.005463 ( 0.005463)
67
+ 300 fields 0.014229 0.000121 0.014350 ( 0.014348)
68
+ 10 fields (nested) 0.002027 0.000069 0.002096 ( 0.002104)
69
+ 50 fields (nested) 0.029933 0.000087 0.030020 ( 0.030040)
70
+ 100 fields (nested) 0.133933 0.000502 0.134435 ( 0.134756)
71
+ 200 fields (nested) 0.495052 0.003545 0.498597 ( 0.499452)
72
+ 300 fields (nested) 1.041463 0.005130 1.046593 ( 1.047137)
73
+ ```
74
+
75
+ Results gathered from my MacBook Pro Mid 2014 (2,5 GHz Quad-Core Intel Core i7, 16 GB 1600 MHz DDR3).
@@ -1,5 +1,5 @@
1
1
  source "https://rubygems.org"
2
2
 
3
- gem "graphql", "~> 1.8.0"
3
+ gem "graphql", "~> 1.11.0"
4
4
 
5
5
  gemspec path: "../"
@@ -1,5 +1,5 @@
1
1
  source "https://rubygems.org"
2
2
 
3
- gem "graphql", "~> 1.9.0"
3
+ gem "graphql", "~> 1.12.0"
4
4
 
5
5
  gemspec path: "../"
@@ -0,0 +1,5 @@
1
+ source "https://rubygems.org"
2
+
3
+ gem "graphql", "~> 1.12.4"
4
+
5
+ gemspec path: "../"
@@ -22,7 +22,7 @@ Gem::Specification.new do |spec|
22
22
 
23
23
  spec.required_ruby_version = ">= 2.3"
24
24
 
25
- spec.add_dependency "graphql", ">= 1.8"
25
+ spec.add_dependency "graphql", ">= 1.10"
26
26
 
27
27
  spec.add_development_dependency "rspec", "~> 3.9"
28
28
  spec.add_development_dependency "rake", ">= 10.0"
@@ -1,17 +1,27 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "graphql/persisted_queries/resolver_helpers"
4
+ require "graphql/persisted_queries/errors"
3
5
  require "graphql/persisted_queries/error_handlers"
4
6
  require "graphql/persisted_queries/schema_patch"
5
7
  require "graphql/persisted_queries/store_adapters"
6
8
  require "graphql/persisted_queries/version"
7
9
  require "graphql/persisted_queries/builder_helpers"
8
10
 
11
+ require "graphql/persisted_queries/compiled_queries/resolver"
12
+ require "graphql/persisted_queries/compiled_queries/multiplex_patch"
13
+ require "graphql/persisted_queries/compiled_queries/query_patch"
14
+
9
15
  module GraphQL
10
16
  # Plugin definition
11
17
  module PersistedQueries
12
- def self.use(schema_defn, options = {})
18
+ # rubocop:disable Metrics/MethodLength
19
+ def self.use(schema_defn, **options)
13
20
  schema = schema_defn.is_a?(Class) ? schema_defn : schema_defn.target
14
- SchemaPatch.patch(schema)
21
+
22
+ compiled_queries = options.delete(:compiled_queries)
23
+ SchemaPatch.patch(schema, compiled_queries)
24
+ configure_compiled_queries if compiled_queries
15
25
 
16
26
  schema.hash_generator = options.delete(:hash_generator) || :sha256
17
27
 
@@ -23,7 +33,20 @@ module GraphQL
23
33
  schema.persisted_queries_tracing_enabled = options.delete(:tracing)
24
34
 
25
35
  store = options.delete(:store) || :memory
26
- schema.configure_persisted_query_store(store, options)
36
+ schema.configure_persisted_query_store(store, **options)
37
+ end
38
+ # rubocop:enable Metrics/MethodLength
39
+
40
+ def self.configure_compiled_queries
41
+ if Gem::Dependency.new("graphql", "< 1.12.0").match?("graphql", GraphQL::VERSION)
42
+ raise ArgumentError, "compiled_queries are not supported for graphql-ruby < 1.12.0"
43
+ end
44
+
45
+ GraphQL::Execution::Multiplex.singleton_class.prepend(
46
+ GraphQL::PersistedQueries::CompiledQueries::MultiplexPatch
47
+ )
48
+
49
+ GraphQL::Query.prepend(GraphQL::PersistedQueries::CompiledQueries::QueryPatch)
27
50
  end
28
51
  end
29
52
  end
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module PersistedQueries
5
+ module CompiledQueries
6
+ # Patches GraphQL::Execution::Multiplex to support compiled queries
7
+ module MultiplexPatch
8
+ if Gem::Dependency.new("graphql", ">= 1.12.4").match?("graphql", GraphQL::VERSION)
9
+ def begin_query(results, idx, query, multiplex)
10
+ return super unless query.persisted_query_not_found?
11
+
12
+ results[idx] = add_not_found_error(query)
13
+ end
14
+ else
15
+ def begin_query(query, multiplex)
16
+ return super unless query.persisted_query_not_found?
17
+
18
+ add_not_found_error(query)
19
+ end
20
+ end
21
+
22
+ def add_not_found_error(query)
23
+ query.context.errors.clear
24
+ query.context.errors << GraphQL::ExecutionError.new("PersistedQueryNotFound")
25
+ GraphQL::Execution::Multiplex::NO_OPERATION
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module PersistedQueries
5
+ module CompiledQueries
6
+ # Patches GraphQL::Query to support compiled queries
7
+ module QueryPatch
8
+ def persisted_query_not_found?
9
+ @persisted_query_not_found
10
+ end
11
+
12
+ def prepare_ast
13
+ return super unless @context[:extensions]
14
+
15
+ @document = resolver.fetch
16
+ not_loaded_document = @document.nil?
17
+
18
+ @persisted_query_not_found = not_loaded_document && query_string.nil?
19
+
20
+ super.tap do
21
+ resolver.persist(query_string, @document) if not_loaded_document && query_string
22
+ end
23
+ end
24
+
25
+ private
26
+
27
+ def resolver
28
+ @resolver ||= Resolver.new(@schema, @context[:extensions])
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,38 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module PersistedQueries
5
+ module CompiledQueries
6
+ # Fetches and persists compiled query
7
+ class Resolver
8
+ include GraphQL::PersistedQueries::ResolverHelpers
9
+
10
+ def initialize(schema, extensions)
11
+ @schema = schema
12
+ @extensions = extensions
13
+ end
14
+
15
+ def fetch
16
+ return if hash.nil?
17
+
18
+ with_error_handling do
19
+ compiled_query = @schema.persisted_query_store.fetch_query(hash, compiled_query: true)
20
+ Marshal.load(compiled_query) if compiled_query # rubocop:disable Security/MarshalLoad
21
+ end
22
+ end
23
+
24
+ def persist(query_string, compiled_query)
25
+ return if hash.nil?
26
+
27
+ validate_hash!(query_string)
28
+
29
+ with_error_handling do
30
+ @schema.persisted_query_store.save_query(
31
+ hash, Marshal.dump(compiled_query), compiled_query: true
32
+ )
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
@@ -7,13 +7,13 @@ module GraphQL
7
7
  module PersistedQueries
8
8
  # Contains factory methods for error handlers
9
9
  module ErrorHandlers
10
- def self.build(handler, options = nil)
10
+ def self.build(handler, **options)
11
11
  if handler.is_a?(ErrorHandlers::BaseErrorHandler)
12
12
  handler
13
13
  elsif handler.is_a?(Proc)
14
14
  build_from_proc(handler)
15
15
  else
16
- build_by_name(handler, options)
16
+ build_by_name(handler, **options)
17
17
  end
18
18
  end
19
19
 
@@ -25,8 +25,8 @@ module GraphQL
25
25
  proc
26
26
  end
27
27
 
28
- def self.build_by_name(name, options)
29
- const_get("#{BuilderHelpers.camelize(name)}ErrorHandler").new(options || {})
28
+ def self.build_by_name(name, **options)
29
+ const_get("#{BuilderHelpers.camelize(name)}ErrorHandler").new(**options)
30
30
  rescue NameError => e
31
31
  raise e.class, "Persisted query error handler for :#{name} haven't been found", e.backtrace
32
32
  end
@@ -5,7 +5,7 @@ module GraphQL
5
5
  module ErrorHandlers
6
6
  # Base class for all error handlers
7
7
  class BaseErrorHandler
8
- def initialize(_options); end
8
+ def initialize(**_options); end
9
9
 
10
10
  def call(_error)
11
11
  raise NotImplementedError
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module PersistedQueries
5
+ # Raised when persisted query is not found in the storage
6
+ class NotFound < StandardError
7
+ def message
8
+ "PersistedQueryNotFound"
9
+ end
10
+ end
11
+
12
+ # Raised when provided hash is not matched with query
13
+ class WrongHash < StandardError
14
+ def message
15
+ "Wrong hash was passed"
16
+ end
17
+ end
18
+ end
19
+ end
@@ -4,7 +4,7 @@ module GraphQL
4
4
  module PersistedQueries
5
5
  # Resolves multiplex query
6
6
  class MultiplexResolver
7
- def initialize(schema, queries, kwargs)
7
+ def initialize(schema, queries, **kwargs)
8
8
  @schema = schema
9
9
  @queries = queries
10
10
  @kwargs = kwargs
@@ -33,15 +33,16 @@ module GraphQL
33
33
  return unless extensions
34
34
 
35
35
  query_params[:query] = Resolver.new(extensions, @schema).resolve(query_params[:query])
36
- rescue Resolver::NotFound, Resolver::WrongHash => e
36
+ rescue GraphQL::PersistedQueries::NotFound, GraphQL::PersistedQueries::WrongHash => e
37
37
  values = { "errors" => [{ "message" => e.message }] }
38
- results[pos] = GraphQL::Query::Result.new(query: GraphQL::Query.new(@schema, query_params[:query]), values: values)
38
+ query = GraphQL::Query.new(@schema, query_params[:query])
39
+ results[pos] = GraphQL::Query::Result.new(query: query, values: values)
39
40
  end
40
41
 
41
42
  def perform_multiplex
42
43
  resolve_idx = (0...@queries.count).select { |i| results[i].nil? }
43
44
  multiplex_result = @schema.multiplex_original(
44
- resolve_idx.map { |i| @queries.at(i) }, @kwargs
45
+ resolve_idx.map { |i| @queries.at(i) }, **@kwargs
45
46
  )
46
47
  resolve_idx.each_with_index { |res_i, mult_i| results[res_i] = multiplex_result[mult_i] }
47
48
  end
@@ -4,54 +4,32 @@ module GraphQL
4
4
  module PersistedQueries
5
5
  # Fetches or stores query string in the storage
6
6
  class Resolver
7
- # Raised when persisted query is not found in the storage
8
- class NotFound < StandardError
9
- def message
10
- "PersistedQueryNotFound"
11
- end
12
- end
13
-
14
- # Raised when provided hash is not matched with query
15
- class WrongHash < StandardError
16
- def message
17
- "Wrong hash was passed"
18
- end
19
- end
7
+ include GraphQL::PersistedQueries::ResolverHelpers
20
8
 
21
9
  def initialize(extensions, schema)
22
10
  @extensions = extensions
23
11
  @schema = schema
24
12
  end
25
13
 
26
- def resolve(query_str)
27
- return query_str if hash.nil?
14
+ def resolve(query_string)
15
+ return query_string if hash.nil?
28
16
 
29
- if query_str
30
- persist_query(query_str)
17
+ if query_string
18
+ persist_query(query_string)
31
19
  else
32
- query_str = with_error_handling { @schema.persisted_query_store.fetch_query(hash) }
33
- raise NotFound if query_str.nil?
20
+ query_string = with_error_handling { @schema.persisted_query_store.fetch_query(hash) }
21
+ raise GraphQL::PersistedQueries::NotFound if query_string.nil?
34
22
  end
35
23
 
36
- query_str
24
+ query_string
37
25
  end
38
26
 
39
27
  private
40
28
 
41
- def with_error_handling
42
- yield
43
- rescue StandardError => e
44
- @schema.persisted_query_error_handler.call(e)
45
- end
46
-
47
- def persist_query(query_str)
48
- raise WrongHash if @schema.hash_generator_proc.call(query_str) != hash
49
-
50
- with_error_handling { @schema.persisted_query_store.save_query(hash, query_str) }
51
- end
29
+ def persist_query(query_string)
30
+ validate_hash!(query_string)
52
31
 
53
- def hash
54
- @hash ||= @extensions.dig("persistedQuery", "sha256Hash")
32
+ with_error_handling { @schema.persisted_query_store.save_query(hash, query_string) }
55
33
  end
56
34
  end
57
35
  end
@@ -0,0 +1,26 @@
1
+ # frozen_string_literal: true
2
+
3
+ module GraphQL
4
+ module PersistedQueries
5
+ # Helper functions for resolvers
6
+ module ResolverHelpers
7
+ module_function
8
+
9
+ def with_error_handling
10
+ yield
11
+ rescue StandardError => e
12
+ @schema.persisted_query_error_handler.call(e)
13
+ end
14
+
15
+ def validate_hash!(query_string)
16
+ return if @schema.hash_generator_proc.call(query_string) == hash
17
+
18
+ raise GraphQL::PersistedQueries::WrongHash
19
+ end
20
+
21
+ def hash
22
+ @hash ||= @extensions.dig("persistedQuery", "sha256Hash")
23
+ end
24
+ end
25
+ end
26
+ end
@@ -10,21 +10,39 @@ module GraphQL
10
10
  # Patches GraphQL::Schema to support persisted queries
11
11
  module SchemaPatch
12
12
  class << self
13
- def patch(schema)
14
- schema.singleton_class.class_eval { alias_method :multiplex_original, :multiplex }
13
+ def patch(schema, compiled_queries)
15
14
  schema.singleton_class.prepend(SchemaPatch)
15
+
16
+ return if compiled_queries
17
+
18
+ schema.singleton_class.class_eval { alias_method :multiplex_original, :multiplex }
19
+ schema.singleton_class.prepend(MultiplexPatch)
20
+ end
21
+ end
22
+
23
+ # Patches GraphQL::Schema to override multiplex (not needed for compiled queries)
24
+ module MultiplexPatch
25
+ def multiplex(queries, **kwargs)
26
+ MultiplexResolver.new(self, queries, **kwargs).resolve
16
27
  end
17
28
  end
18
29
 
19
- attr_reader :persisted_query_store, :hash_generator_proc, :persisted_query_error_handler
20
30
  attr_writer :persisted_queries_tracing_enabled
21
31
 
22
- def configure_persisted_query_store(store, options)
23
- @persisted_query_store = StoreAdapters.build(store, options).tap do |adapter|
32
+ def configure_persisted_query_store(store, **options)
33
+ @persisted_query_store = StoreAdapters.build(store, **options).tap do |adapter|
24
34
  adapter.tracers = tracers if persisted_queries_tracing_enabled?
25
35
  end
26
36
  end
27
37
 
38
+ def persisted_query_store
39
+ @persisted_query_store ||= find_inherited_value(:persisted_query_store)
40
+ end
41
+
42
+ def persisted_query_error_handler
43
+ @persisted_query_error_handler ||= find_inherited_value(:persisted_query_error_handler)
44
+ end
45
+
28
46
  def configure_persisted_query_error_handler(handler)
29
47
  @persisted_query_error_handler = ErrorHandlers.build(handler)
30
48
  end
@@ -33,22 +51,17 @@ module GraphQL
33
51
  @hash_generator_proc = HashGeneratorBuilder.new(hash_generator).build
34
52
  end
35
53
 
36
- def verify_http_method=(verify)
37
- return unless verify
38
-
39
- if graphql10?
40
- query_analyzer(prepare_analyzer)
41
- else
42
- query_analyzers << prepare_analyzer
43
- end
54
+ def hash_generator_proc
55
+ @hash_generator_proc ||= find_inherited_value(:hash_generator_proc)
44
56
  end
45
57
 
46
- def persisted_queries_tracing_enabled?
47
- @persisted_queries_tracing_enabled
58
+ def verify_http_method=(verify)
59
+ query_analyzer(prepare_analyzer) if verify
48
60
  end
49
61
 
50
- def multiplex(queries, **kwargs)
51
- MultiplexResolver.new(self, queries, kwargs).resolve
62
+ def persisted_queries_tracing_enabled?
63
+ @persisted_queries_tracing_enabled ||=
64
+ find_inherited_value(:persisted_queries_tracing_enabled?)
52
65
  end
53
66
 
54
67
  def tracer(name)
@@ -62,12 +75,8 @@ module GraphQL
62
75
 
63
76
  private
64
77
 
65
- def graphql10?
66
- Gem::Dependency.new("graphql", ">= 1.10.0").match?("graphql", GraphQL::VERSION)
67
- end
68
-
69
78
  def prepare_analyzer
70
- if graphql10? && using_ast_analysis?
79
+ if using_ast_analysis?
71
80
  require "graphql/persisted_queries/analyzers/http_method_ast_analyzer"
72
81
  Analyzers::HttpMethodAstAnalyzer
73
82
  else
@@ -10,16 +10,16 @@ module GraphQL
10
10
  module PersistedQueries
11
11
  # Contains factory methods for store adapters
12
12
  module StoreAdapters
13
- def self.build(adapter, options = nil)
13
+ def self.build(adapter, **options)
14
14
  if adapter.is_a?(StoreAdapters::BaseStoreAdapter)
15
15
  adapter
16
16
  else
17
- build_by_name(adapter, options)
17
+ build_by_name(adapter, **options)
18
18
  end
19
19
  end
20
20
 
21
- def self.build_by_name(name, options)
22
- const_get("#{BuilderHelpers.camelize(name)}StoreAdapter").new(options || {})
21
+ def self.build_by_name(name, **options)
22
+ const_get("#{BuilderHelpers.camelize(name)}StoreAdapter").new(**options)
23
23
  rescue NameError => e
24
24
  raise e.class, "Persisted query store adapter for :#{name} haven't been found", e.backtrace
25
25
  end
@@ -8,19 +8,22 @@ module GraphQL
8
8
  include GraphQL::Tracing::Traceable
9
9
  attr_writer :tracers
10
10
 
11
- def initialize(_options)
11
+ def initialize(**_options)
12
12
  @name = :base
13
13
  end
14
14
 
15
- def fetch_query(hash)
16
- fetch(hash).tap do |result|
15
+ def fetch_query(hash, compiled_query: false)
16
+ key = build_key(hash, compiled_query)
17
+
18
+ fetch(key).tap do |result|
17
19
  event = result ? "cache_hit" : "cache_miss"
18
20
  trace("fetch_query.#{event}", adapter: @name)
19
21
  end
20
22
  end
21
23
 
22
- def save_query(hash, query)
23
- trace("save_query", adapter: @name) { save(hash, query) }
24
+ def save_query(hash, query, compiled_query: false)
25
+ key = build_key(hash, compiled_query)
26
+ trace("save_query", adapter: @name) { save(key, query) }
24
27
  end
25
28
 
26
29
  protected
@@ -41,6 +44,13 @@ module GraphQL
41
44
  yield
42
45
  end
43
46
  end
47
+
48
+ private
49
+
50
+ def build_key(hash, compiled_query)
51
+ key = "#{RUBY_ENGINE}-#{RUBY_VERSION}:#{GraphQL::VERSION}:#{hash}"
52
+ compiled_query ? "compiled:#{key}" : key
53
+ end
44
54
  end
45
55
  end
46
56
  end
@@ -35,7 +35,7 @@ module GraphQL
35
35
 
36
36
  def build_dalli_proc(dalli_client)
37
37
  if dalli_client.is_a?(Hash)
38
- build_dalli_proc(MemcachedClientBuilder.new(dalli_client).build)
38
+ build_dalli_proc(MemcachedClientBuilder.new(**dalli_client).build)
39
39
  elsif dalli_client.is_a?(Proc)
40
40
  dalli_client
41
41
  elsif defined?(::Dalli::Client) && dalli_client.is_a?(::Dalli::Client)
@@ -5,7 +5,7 @@ module GraphQL
5
5
  module StoreAdapters
6
6
  # Memory adapter for storing persisted queries
7
7
  class MemoryStoreAdapter < BaseStoreAdapter
8
- def initialize(_options)
8
+ def initialize(**_options)
9
9
  @storage = {}
10
10
  @name = :memory
11
11
  end
@@ -38,7 +38,7 @@ module GraphQL
38
38
  # rubocop: disable Metrics/PerceivedComplexity
39
39
  def build_redis_proc(redis_client)
40
40
  if redis_client.is_a?(Hash)
41
- build_redis_proc(RedisClientBuilder.new(redis_client).build)
41
+ build_redis_proc(RedisClientBuilder.new(**redis_client).build)
42
42
  elsif redis_client.is_a?(Proc)
43
43
  redis_client
44
44
  elsif defined?(::Redis) && redis_client.is_a?(::Redis)
@@ -18,7 +18,7 @@ module GraphQL
18
18
  expiration: expiration,
19
19
  namespace: namespace
20
20
  )
21
- @memory_adapter = memory_adapter_class.new(nil)
21
+ @memory_adapter = memory_adapter_class.new
22
22
  @name = :redis_with_local_cache
23
23
  end
24
24
 
@@ -2,6 +2,6 @@
2
2
 
3
3
  module GraphQL
4
4
  module PersistedQueries
5
- VERSION = "1.0.2"
5
+ VERSION = "1.2.2"
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: graphql-persisted_queries
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.2
4
+ version: 1.2.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - DmitryTsepelev
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-06-29 00:00:00.000000000 Z
11
+ date: 2021-04-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: graphql
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - ">="
18
18
  - !ruby/object:Gem::Version
19
- version: '1.8'
19
+ version: '1.10'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - ">="
25
25
  - !ruby/object:Gem::Version
26
- version: '1.8'
26
+ version: '1.10'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: rspec
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -115,24 +115,31 @@ executables: []
115
115
  extensions: []
116
116
  extra_rdoc_files: []
117
117
  files:
118
+ - ".github/workflows/rspec.yml"
119
+ - ".github/workflows/rubocop.yml"
118
120
  - ".gitignore"
119
121
  - ".rubocop.yml"
120
- - ".travis.yml"
121
122
  - CHANGELOG.md
122
123
  - Gemfile
123
124
  - LICENSE.txt
124
125
  - README.md
125
126
  - Rakefile
127
+ - benchmark/compiled_queries.rb
128
+ - benchmark/helpers.rb
129
+ - benchmark/persisted_queries.rb
130
+ - benchmark/plain_gql.rb
126
131
  - bin/console
127
132
  - bin/setup
128
133
  - docs/alternative_stores.md
134
+ - docs/compiled_queries_benchmark.md
129
135
  - docs/error_handling.md
130
136
  - docs/hash.md
131
137
  - docs/http_cache.md
132
138
  - docs/tracing.md
133
139
  - gemfiles/graphql_1_10.gemfile
134
- - gemfiles/graphql_1_8.gemfile
135
- - gemfiles/graphql_1_9.gemfile
140
+ - gemfiles/graphql_1_11.gemfile
141
+ - gemfiles/graphql_1_12_0.gemfile
142
+ - gemfiles/graphql_1_12_4.gemfile
136
143
  - gemfiles/graphql_master.gemfile
137
144
  - graphql-persisted_queries.gemspec
138
145
  - lib/graphql/persisted_queries.rb
@@ -140,12 +147,17 @@ files:
140
147
  - lib/graphql/persisted_queries/analyzers/http_method_ast_analyzer.rb
141
148
  - lib/graphql/persisted_queries/analyzers/http_method_validator.rb
142
149
  - lib/graphql/persisted_queries/builder_helpers.rb
150
+ - lib/graphql/persisted_queries/compiled_queries/multiplex_patch.rb
151
+ - lib/graphql/persisted_queries/compiled_queries/query_patch.rb
152
+ - lib/graphql/persisted_queries/compiled_queries/resolver.rb
143
153
  - lib/graphql/persisted_queries/error_handlers.rb
144
154
  - lib/graphql/persisted_queries/error_handlers/base_error_handler.rb
145
155
  - lib/graphql/persisted_queries/error_handlers/default_error_handler.rb
156
+ - lib/graphql/persisted_queries/errors.rb
146
157
  - lib/graphql/persisted_queries/hash_generator_builder.rb
147
158
  - lib/graphql/persisted_queries/multiplex_resolver.rb
148
159
  - lib/graphql/persisted_queries/resolver.rb
160
+ - lib/graphql/persisted_queries/resolver_helpers.rb
149
161
  - lib/graphql/persisted_queries/schema_patch.rb
150
162
  - lib/graphql/persisted_queries/store_adapters.rb
151
163
  - lib/graphql/persisted_queries/store_adapters/base_store_adapter.rb
@@ -160,7 +172,7 @@ homepage: https://github.com/DmitryTsepelev/graphql-ruby-persisted_queries
160
172
  licenses:
161
173
  - MIT
162
174
  metadata: {}
163
- post_install_message:
175
+ post_install_message:
164
176
  rdoc_options: []
165
177
  require_paths:
166
178
  - lib
@@ -175,8 +187,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
175
187
  - !ruby/object:Gem::Version
176
188
  version: '0'
177
189
  requirements: []
178
- rubygems_version: 3.0.3
179
- signing_key:
190
+ rubygems_version: 3.1.2
191
+ signing_key:
180
192
  specification_version: 4
181
193
  summary: Persisted queries for graphql-ruby
182
194
  test_files: []
data/.travis.yml DELETED
@@ -1,24 +0,0 @@
1
- language: ruby
2
- cache: bundler
3
-
4
- rvm:
5
- - 2.3
6
- - 2.4
7
- - 2.5
8
- - 2.6
9
- - ruby-head
10
-
11
- gemfile:
12
- - gemfiles/graphql_1_8.gemfile
13
- - gemfiles/graphql_1_9.gemfile
14
- - gemfiles/graphql_1_10.gemfile
15
- - gemfiles/graphql_master.gemfile
16
-
17
-
18
- notifications:
19
- email: false
20
-
21
- matrix:
22
- fast_finish: true
23
- allow_failures:
24
- - rvm: ruby-head