quail-graphql 0.1.0

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 (38) hide show
  1. checksums.yaml +7 -0
  2. data/AGENTS.md +19 -0
  3. data/LICENSE.txt +21 -0
  4. data/README.md +39 -0
  5. data/Rakefile +12 -0
  6. data/lib/generators/quail/channel_generator.rb +17 -0
  7. data/lib/generators/quail/install_generator.rb +75 -0
  8. data/lib/generators/quail/resource_generator.rb +79 -0
  9. data/lib/generators/quail/templates/graphql_channel.rb.tt +4 -0
  10. data/lib/generators/quail/templates/graphql_channel_custom.rb.tt +23 -0
  11. data/lib/generators/quail/templates/graphql_controller.rb.tt +40 -0
  12. data/lib/generators/quail/templates/initializer.rb.tt +5 -0
  13. data/lib/generators/quail/templates/resource.rb.tt +23 -0
  14. data/lib/generators/quail/templates/schema.rb.tt +21 -0
  15. data/lib/quail/channel.rb +52 -0
  16. data/lib/quail/controller_helpers.rb +27 -0
  17. data/lib/quail/railtie.rb +41 -0
  18. data/lib/quail/resource/dsl.rb +121 -0
  19. data/lib/quail/resource/mutation_builder/context.rb +22 -0
  20. data/lib/quail/resource/mutation_builder/resolvers.rb +42 -0
  21. data/lib/quail/resource/mutation_builder.rb +139 -0
  22. data/lib/quail/resource/query_builder.rb +42 -0
  23. data/lib/quail/resource/subscription_builder.rb +53 -0
  24. data/lib/quail/resource/type_builder/association_builder.rb +92 -0
  25. data/lib/quail/resource/type_builder/field_builder.rb +57 -0
  26. data/lib/quail/resource/type_builder.rb +68 -0
  27. data/lib/quail/resource.rb +33 -0
  28. data/lib/quail/schema_builder/discovery.rb +42 -0
  29. data/lib/quail/schema_builder/type_definitions.rb +44 -0
  30. data/lib/quail/schema_builder.rb +127 -0
  31. data/lib/quail/tasks/quail.rake +25 -0
  32. data/lib/quail/type_map.rb +31 -0
  33. data/lib/quail/version.rb +5 -0
  34. data/lib/quail.rb +99 -0
  35. data/quail_logo.png +0 -0
  36. data/quail_logo_new.svg +129 -0
  37. data/sig/quail.rbs +4 -0
  38. metadata +123 -0
@@ -0,0 +1,127 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "schema_builder/discovery"
4
+ require_relative "schema_builder/type_definitions"
5
+
6
+ module Quail
7
+ # Assembles the full GraphQL schema from registered resources, custom queries, and mutations.
8
+ module SchemaBuilder
9
+ @configure_mutex = Mutex.new
10
+
11
+ def self.call(schema_class, &block)
12
+ schema_class.instance_variable_set(:@quail_configured, false)
13
+ install_lazy_hooks(schema_class)
14
+ block&.call(schema_class)
15
+ end
16
+
17
+ def self.install_lazy_hooks(schema_class)
18
+ %i[multiplex execute to_definition].each do |method_name|
19
+ schema_class.define_singleton_method(method_name) do |*args, **kwargs|
20
+ Quail::SchemaBuilder.configure!(self) unless @quail_configured
21
+ super(*args, **kwargs)
22
+ end
23
+ end
24
+ end
25
+
26
+ def self.configure!(schema_class)
27
+ @configure_mutex.synchronize do
28
+ return if schema_class.instance_variable_get(:@quail_configured)
29
+
30
+ eager_load_resources if defined?(Rails)
31
+ Resource::TypeBuilder.build_all
32
+ eager_load_resolvers if defined?(Rails)
33
+ attach_root_types(schema_class)
34
+ install_defaults(schema_class)
35
+ schema_class.instance_variable_set(:@quail_configured, true)
36
+ end
37
+ end
38
+
39
+ def self.eager_load_resources
40
+ Dir[Rails.root.join("app/graphql/resources/**/*.rb")].each { |f| require f }
41
+ end
42
+
43
+ def self.eager_load_resolvers
44
+ %w[mutations queries].each do |dir|
45
+ Dir[Rails.root.join("app/graphql/#{dir}/**/*.rb")].each { |f| require f }
46
+ end
47
+ end
48
+
49
+ def self.attach_root_types(schema_class)
50
+ query_type = build_query_type
51
+ mutation_type = build_mutation_type
52
+ subscription_type = build_subscription_type
53
+
54
+ schema_class.query(query_type) if query_type
55
+ schema_class.mutation(mutation_type) if mutation_type
56
+ schema_class.subscription(subscription_type) if subscription_type
57
+ end
58
+
59
+ def self.install_defaults(schema_class)
60
+ schema_class.use GraphQL::Dataloader unless schema_class.dataloader_class
61
+ schema_class.use GraphQL::Subscriptions::ActionCableSubscriptions unless schema_class.subscriptions
62
+ end
63
+
64
+ def self.build_query_type
65
+ fields = collect_resource_query_fields
66
+ custom = Discovery.custom_queries
67
+ extra = Quail.extra_queries
68
+ return nil if fields.empty? && extra.empty? && custom.empty?
69
+
70
+ create_query_class(fields, custom, extra)
71
+ end
72
+
73
+ def self.create_query_class(fields, custom, extra)
74
+ base = Quail.base_object_class || GraphQL::Schema::Object
75
+ Class.new(base) do
76
+ graphql_name "Query"
77
+ TypeDefinitions.define_query_fields(self, fields)
78
+ custom.each { |name, klass| field name, resolver: klass }
79
+ TypeDefinitions.define_extra_query_fields(self, extra)
80
+ end
81
+ end
82
+
83
+ def self.collect_resource_query_fields
84
+ fields = {}
85
+ Quail.registry.each_value { |r| fields.merge!(r.query_fields) }
86
+ fields
87
+ end
88
+
89
+ def self.build_mutation_type
90
+ mutations = collect_all_mutations
91
+ return nil if mutations.empty?
92
+
93
+ base = Quail.base_object_class || GraphQL::Schema::Object
94
+ Class.new(base) do
95
+ graphql_name "Mutation"
96
+ mutations.each { |name, klass| field name, mutation: klass }
97
+ end
98
+ end
99
+
100
+ def self.collect_all_mutations
101
+ mutations = collect_resource_mutations
102
+ Discovery.custom_mutations.each { |name, klass| mutations[name] = klass }
103
+ Quail.extra_mutations.each { |name, klass| mutations[name.to_sym] = klass }
104
+ mutations
105
+ end
106
+
107
+ def self.collect_resource_mutations
108
+ mutations = {}
109
+ Quail.registry.each_value do |r|
110
+ r.mutations.each { |action, klass| mutations[:"#{r.model_class.name.underscore}_#{action}"] = klass }
111
+ end
112
+ mutations
113
+ end
114
+
115
+ def self.build_subscription_type
116
+ fields = {}
117
+ Quail.registry.each_value { |r| fields.merge!(r.subscription_fields) }
118
+ return nil if fields.empty?
119
+
120
+ base = Quail.base_object_class || GraphQL::Schema::Object
121
+ Class.new(base) do
122
+ graphql_name "Subscription"
123
+ TypeDefinitions.define_subscription_fields(self, fields)
124
+ end
125
+ end
126
+ end
127
+ end
@@ -0,0 +1,25 @@
1
+ # frozen_string_literal: true
2
+
3
+ namespace :quail do
4
+ desc "Export the GraphQL schema to SDL (schema.graphql)"
5
+ task dump: :environment do
6
+ schema_class = Rails.application.config.quail.schema_class
7
+ abort "Set config.quail.schema_class in your config/initializer" unless schema_class
8
+
9
+ path = ENV.fetch("SCHEMA_PATH", "schema.graphql")
10
+ File.write(path, schema_class.to_definition)
11
+ puts "GraphQL Schema written to #{path}"
12
+ end
13
+
14
+ desc "Export the GraphQL schema to JSON (schema.json)"
15
+ task dump_json: :environment do
16
+ schema_class = Rails.application.config.quail.schema_class
17
+ abort "Set config.quail.schema_class in your config/initializer" unless schema_class
18
+
19
+ path = ENV.fetch("SCHEMA_PATH", "schema.json")
20
+ File.write(path, schema_class.to_definition)
21
+ result = schema_class.execute(GraphQL::Introspection::INTROSPECTION_QUERY)
22
+ File.write(path, JSON.pretty_generate(result.to_h))
23
+ puts "GraphQL JSON Schema written to #{path}"
24
+ end
25
+ end
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Quail
4
+ # Maps ActiveRecord column types to their corresponding GraphQL type classes.
5
+ module TypeMap
6
+ MAPPING = {
7
+ integer: GraphQL::Types::Int,
8
+ bigint: GraphQL::Types::BigInt,
9
+ float: GraphQL::Types::Float,
10
+ decimal: GraphQL::Types::Float,
11
+ string: GraphQL::Types::String,
12
+ text: GraphQL::Types::String,
13
+ boolean: GraphQL::Types::Boolean,
14
+ date: GraphQL::Types::ISO8601Date,
15
+ datetime: GraphQL::Types::ISO8601DateTime,
16
+ time: GraphQL::Types::ISO8601DateTime,
17
+ json: GraphQL::Types::JSON,
18
+ jsonb: GraphQL::Types::JSON
19
+ }.freeze
20
+
21
+ def self.graphql_types(column)
22
+ return GraphQL::Types::ID if column.name == "id"
23
+
24
+ MAPPING[column.type] || GraphQL::Types::String
25
+ end
26
+
27
+ def self.nullable?(column)
28
+ column.null
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Quail
4
+ VERSION = "0.1.0"
5
+ end
data/lib/quail.rb ADDED
@@ -0,0 +1,99 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "graphql"
4
+ require "rails"
5
+
6
+ require_relative "quail/version"
7
+ require_relative "quail/type_map"
8
+ require_relative "quail/resource/dsl"
9
+ require_relative "quail/resource/type_builder"
10
+ require_relative "quail/resource/query_builder"
11
+ require_relative "quail/resource/mutation_builder"
12
+ require_relative "quail/resource/subscription_builder"
13
+ require_relative "quail/resource"
14
+ require_relative "quail/schema_builder"
15
+ require_relative "quail/controller_helpers"
16
+ require_relative "quail/channel"
17
+ require_relative "quail/railtie"
18
+
19
+ # Top-level namespace for the Quail GraphQL resource framework.
20
+ module Quail
21
+ class Error < StandardError; end
22
+
23
+ # Wrapper aliases — insulate consuming apps from graphql-ruby internals.
24
+ Object = GraphQL::Schema::Object
25
+ InputObject = GraphQL::Schema::InputObject
26
+ Enum = GraphQL::Schema::Enum
27
+ Schema = GraphQL::Schema
28
+
29
+ # Base mutation class with subscription trigger helper.
30
+ class Mutation < GraphQL::Schema::RelayClassicMutation
31
+ # Trigger a Quail subscription event from a custom mutation.
32
+ #
33
+ # trigger_subscription(:link_created, { user_id: user.id }, link)
34
+ #
35
+ # The arguments must match the subscription's scope declared via subscribe_on.
36
+ def trigger_subscription(event, scope_args, record)
37
+ context.schema.subscriptions&.trigger(event, scope_args, record)
38
+ end
39
+ end
40
+
41
+ # Base resolver class for custom Quail queries with symbol-based type resolution.
42
+ class Query < GraphQL::Schema::Resolver
43
+ # Allows symbol-based type references that resolve to resource graphql types.
44
+ #
45
+ # type :user, null: true # resolves to UserResource.graphql_type
46
+ # type [:article], null: false # resolves to [ArticleResource.graphql_type]
47
+ # type :subscription, connection: true, null: false # resolves to SubscriptionType.connection_type
48
+ # type Types::SessionType, null: false # pass-through, works as normal
49
+ #
50
+ def self.type(type_arg = nil, null: nil, connection: false)
51
+ resolved = resolve_type_arg(type_arg, connection: connection)
52
+ super(resolved, null: null)
53
+ end
54
+
55
+ def self.resolve_type_arg(type_arg, connection: false)
56
+ if type_arg.is_a?(Symbol)
57
+ name = type_arg
58
+ connection ? -> { resolve_resource_type(name).connection_type } : -> { resolve_resource_type(name) }
59
+ elsif type_arg.is_a?(Array) && type_arg.length == 1 && type_arg.first.is_a?(Symbol)
60
+ name = type_arg.first
61
+ -> { [resolve_resource_type(name)] }
62
+ else
63
+ type_arg
64
+ end
65
+ end
66
+ private_class_method :resolve_type_arg
67
+
68
+ def self.resolve_resource_type(name)
69
+ klass = "#{name.to_s.camelize}Resource".constantize
70
+ klass.graphql_type
71
+ end
72
+ end
73
+
74
+ class << self
75
+ attr_accessor :base_object_class, :base_mutation_class, :base_input_class
76
+
77
+ def registry
78
+ @registry ||= {}
79
+ end
80
+
81
+ def extra_mutations
82
+ @extra_mutations ||= {}
83
+ end
84
+
85
+ def extra_queries
86
+ @extra_queries ||= {}
87
+ end
88
+
89
+ # Register a resource class, keyed by its inferred model
90
+ def register(resource_class)
91
+ registry[resource_class.model_class] = resource_class
92
+ end
93
+
94
+ # Lookup resource for a given model class
95
+ def resource_for(model_class)
96
+ registry[model_class]
97
+ end
98
+ end
99
+ end
data/quail_logo.png ADDED
Binary file
@@ -0,0 +1,129 @@
1
+ <?xml version="1.0" standalone="no"?>
2
+ <svg xmlns="http://www.w3.org/2000/svg"
3
+ width="800" height="420" viewBox="0 0 800 420"
4
+ preserveAspectRatio="xMidYMid meet">
5
+
6
+ <!-- Quail bird logo in Ruby/Rails red (scaled down) -->
7
+ <g transform="translate(20,390) scale(0.075,-0.075)"
8
+ fill="#CC342D" stroke="none">
9
+ <path d="M3200 4108 c-148 -22 -280 -141 -345 -310 l-28 -75 -103 5 c-86 4
10
+ -114 1 -176 -18 -141 -42 -247 -120 -358 -260 -23 -30 -85 -143 -138 -250
11
+ -127 -263 -140 -275 -432 -425 -118 -60 -259 -140 -315 -176 -337 -224 -565
12
+ -509 -680 -851 -39 -115 -70 -250 -81 -348 -8 -78 -7 -77 -104 -215 -149 -214
13
+ -305 -437 -333 -476 -16 -22 -26 -46 -24 -54 3 -7 31 -19 62 -26 108 -24 256
14
+ 28 364 127 48 44 65 53 121 63 95 19 292 85 387 131 45 22 87 40 94 40 6 0 26
15
+ -9 44 -20 59 -37 230 -98 340 -122 l110 -24 63 -95 c35 -52 87 -137 117 -189
16
+ l55 -95 -48 -5 c-69 -8 -112 -39 -112 -79 0 -8 138 -11 450 -11 312 0 450 3
17
+ 450 11 0 22 -22 49 -50 64 -21 11 -60 15 -137 15 l-108 0 -105 132 c-58 72
18
+ -107 135 -109 140 -2 6 8 22 22 36 15 15 36 47 49 71 22 41 31 46 143 95 144
19
+ 62 241 122 352 216 250 211 414 534 453 891 24 211 -19 478 -113 714 -70 177
20
+ -63 248 36 381 38 52 53 65 97 79 35 12 68 16 100 12 l48 -6 -8 28 c-21 75
21
+ -64 132 -121 161 -31 16 -37 26 -48 74 -16 70 -62 141 -123 186 -27 19 -48 42
22
+ -48 51 0 29 75 124 123 156 67 45 124 52 184 22 43 -22 52 -33 93 -114 53
23
+ -104 88 -135 156 -135 113 0 167 146 104 286 -58 131 -217 214 -370 192z
24
+ m-308 -531 c50 -30 73 -63 93 -129 15 -53 15 -59 0 -82 l-17 -25 -51 20 c-67
25
+ 27 -65 25 -81 64 -14 33 -59 65 -92 65 -10 0 -32 -5 -51 -12 -38 -14 -57 -3
26
+ -29 18 32 23 8 17 -104 -27 -58 -22 -134 -52 -169 -65 -115 -45 -116 -24 -1
27
+ 38 137 74 208 106 300 134 98 30 155 30 202 1z m-129 -151 c8 -20 -20 -43 -35
28
+ -28 -14 14 -3 42 16 42 7 0 16 -6 19 -14z m-153 -50 c0 -2 -11 -28 -24 -57
29
+ -47 -103 -41 -232 15 -341 36 -70 117 -142 188 -168 41 -16 66 -31 71 -44 10
30
+ -28 3 -29 -75 -11 -90 20 -176 74 -224 138 -66 88 -84 134 -89 222 -6 109 8
31
+ 155 67 216 40 41 71 61 71 45z m-324 -84 c-8 -9 -19 -13 -22 -9 -10 9 16 38
32
+ 28 31 6 -4 4 -13 -6 -22z m10 -90 c-22 -23 -29 -10 -9 18 11 16 18 19 21 11 2
33
+ -7 -3 -20 -12 -29z m-96 -28 c-18 -21 -24 -10 -9 18 8 14 14 18 17 10 2 -7 -2
34
+ -19 -8 -28z m124 -71 c-26 -19 -29 -8 -8 24 16 25 19 26 22 9 2 -11 -4 -25
35
+ -14 -33z m-78 -1 c-7 -22 -36 -38 -36 -20 0 14 31 50 38 44 2 -3 1 -13 -2 -24z
36
+ m114 -66 c0 -8 -9 -24 -20 -37 -17 -21 -19 -22 -20 -6 0 23 18 57 30 57 6 0
37
+ 10 -6 10 -14z m-223 -33 c-25 -26 -40 -10 -15 16 15 17 23 20 26 12 2 -7 -3
38
+ -20 -11 -28z m126 12 c-3 -9 -8 -14 -10 -11 -3 3 -2 9 2 15 9 16 15 13 8 -4z
39
+ m-53 -60 c0 -18 -48 -70 -57 -62 -7 8 36 77 48 77 5 0 9 -7 9 -15z m90 -45 c0
40
+ -15 -59 -77 -60 -62 0 23 30 72 45 72 8 0 15 -4 15 -10z m90 2 c0 -5 -7 -17
41
+ -15 -28 -15 -19 -20 -8 -9 20 6 17 24 22 24 8z m-310 -6 c0 -2 -8 -10 -17 -17
42
+ -16 -13 -17 -12 -4 4 13 16 21 21 21 13z m60 -101 c-7 -8 -18 -15 -24 -15 -6
43
+ 0 -2 7 8 15 25 19 32 19 16 0z m270 4 c0 -6 -5 -19 -11 -30 -15 -28 -31 -13
44
+ -17 16 11 25 28 34 28 14z m-90 -27 c0 -22 -34 -56 -50 -50 -11 3 29 68 43 68
45
+ 4 0 7 -8 7 -18z m568 -139 c-10 -2 -18 -11 -18 -19 0 -8 -7 -17 -16 -21 -12
46
+ -4 -13 -8 -3 -13 17 -11 39 -1 48 23 6 15 12 2 29 -54 25 -86 37 -145 24 -114
47
+ -9 19 -9 19 -21 -3 -9 -18 -16 -20 -30 -12 -16 8 -18 7 -14 -9 5 -20 -11 -35
48
+ -37 -36 -8 0 -15 -5 -15 -12 0 -6 -4 -15 -9 -20 -5 -4 -6 -3 -3 3 9 16 -22 27
49
+ -38 14 -19 -16 -32 9 -30 60 0 25 4 51 8 57 4 6 4 14 -1 17 -4 2 -9 22 -10 43
50
+ -2 21 -4 51 -6 68 -3 26 -2 27 9 11 8 -10 18 -15 24 -11 6 3 11 0 11 -7 1 -8
51
+ 6 -6 15 6 12 16 12 22 2 28 -6 4 12 7 43 7 30 -1 47 -3 38 -6z m-727 -60 c26
52
+ -11 49 -25 53 -31 7 -11 -8 -10 -37 3 -10 4 -20 5 -24 2 -3 -4 -19 1 -35 9
53
+ -41 21 -116 15 -228 -17 -206 -60 -314 -123 -439 -254 -64 -68 -71 -73 -51
54
+ -37 86 153 257 285 432 332 98 27 261 23 329 -7z m819 -273 c0 -5 -5 -10 -11
55
+ -10 -5 0 -7 5 -4 10 3 6 8 10 11 10 2 0 4 -4 4 -10z m-5 -30 c-3 -5 -1 -10 4
56
+ -10 6 0 11 -12 11 -27 0 -21 -3 -24 -9 -13 -6 8 -7 18 -5 22 3 5 -2 11 -11 14
57
+ -13 6 -14 8 -3 15 17 11 20 11 13 -1z m-21 -28 c3 -5 -1 -9 -9 -9 -8 0 -12 4
58
+ -9 9 3 4 7 8 9 8 2 0 6 -4 9 -8z m-1708 -44 c-71 -88 -157 -231 -177 -294 -26
59
+ -80 -26 -81 -38 -68 -14 14 5 101 36 162 15 30 65 94 111 143 85 90 117 116
60
+ 68 57z m1719 2 c3 -5 1 -10 -4 -10 -6 0 -11 5 -11 10 0 6 2 10 4 10 3 0 8 -4
61
+ 11 -10z m-475 -218 c-12 -49 -46 -138 -77 -202 -52 -108 -62 -121 -167 -225
62
+ -171 -170 -354 -270 -573 -314 -56 -12 -127 -21 -160 -21 l-58 1 110 29 c190
63
+ 49 290 91 435 180 262 162 471 446 498 680 l7 55 3 -48 c2 -26 -6 -87 -18
64
+ -135z m-336 92 c-19 -40 -66 -74 -104 -74 -21 0 -15 8 45 64 39 35 71 60 73
65
+ 55 2 -4 -4 -25 -14 -45z m-205 -26 c-5 -18 -9 -34 -9 -35 0 -1 -13 -11 -28
66
+ -22 -17 -12 -37 -18 -50 -14 -19 4 -15 10 35 54 31 27 57 49 59 49 1 0 -2 -15
67
+ -7 -32z m1005 -117 c24 -10 24 -10 11 -68 -19 -81 -61 -194 -106 -288 -46 -94
68
+ -136 -218 -162 -221 -13 -2 -17 2 -13 12 3 9 1 12 -4 9 -6 -3 -10 -13 -10 -21
69
+ 0 -8 -5 -14 -11 -14 -6 0 -8 9 -4 20 8 24 -3 62 -15 55 -5 -3 -11 -1 -14 4 -3
70
+ 5 -15 7 -26 4 -27 -7 -25 9 4 36 25 24 56 79 56 101 0 14 -99 -54 -118 -82 -7
71
+ -10 -17 -16 -22 -13 -5 3 -12 0 -16 -6 -4 -8 -9 -7 -15 2 -7 12 -9 12 -9 1 0
72
+ -8 9 -16 20 -19 27 -7 26 -23 -1 -18 -12 3 -24 7 -27 10 -3 2 -11 0 -18 -6 -9
73
+ -8 -11 -5 -7 10 3 12 10 21 15 21 5 0 6 5 3 10 -4 6 -11 8 -16 5 -5 -4 -9 -1
74
+ -9 4 0 6 4 11 10 11 14 0 60 76 60 100 0 11 -3 20 -6 20 -10 0 -87 -62 -106
75
+ -84 -14 -17 -18 -18 -33 -6 -9 7 -15 9 -14 4 4 -23 -3 -31 -26 -31 -23 0 -21
76
+ 4 33 71 32 39 68 85 80 102 56 81 286 243 376 264 45 11 111 11 140 1z m-1994
77
+ -140 c0 -17 -11 -50 -24 -75 -13 -25 -27 -68 -31 -96 -6 -44 -9 -49 -22 -38
78
+ -22 18 -11 91 26 172 32 71 51 84 51 37z m850 -185 c0 -2 -7 -7 -16 -10 -8 -3
79
+ -12 -2 -9 4 6 10 25 14 25 6z m-384 -68 c4 -7 3 -8 -4 -4 -6 4 -22 1 -34 -5
80
+ -21 -11 -22 -11 -9 4 16 20 37 22 47 5z m-591 -27 c3 -5 1 -12 -5 -16 -5 -3
81
+ -10 1 -10 9 0 18 6 21 15 7z m1535 -35 c0 -2 -7 -7 -16 -10 -8 -3 -12 -2 -9 4
82
+ 6 10 25 14 25 6z m-1596 -71 c-10 -16 -20 -23 -22 -16 -4 12 28 55 35 47 3 -2
83
+ -3 -17 -13 -31z m1473 20 c0 -8 -4 -15 -8 -15 -4 0 -16 -3 -26 -7 -12 -4 -10
84
+ 0 7 15 14 12 25 21 26 22 0 0 1 -7 1 -15z m183 5 c0 -5 -4 -10 -10 -10 -5 0
85
+ -10 5 -10 10 0 6 5 10 10 10 6 0 10 -4 10 -10z m120 -64 c0 -3 -4 -8 -10 -11
86
+ -5 -3 -10 -1 -10 4 0 6 5 11 10 11 6 0 10 -2 10 -4z m-1538 -13 c-6 -2 -10 -9
87
+ -7 -14 4 -5 -1 -6 -10 -2 -13 5 -14 7 -3 14 7 5 18 8 23 8 6 0 4 -3 -3 -6z
88
+ m1301 -4 c12 -7 23 -13 25 -14 2 -2 -6 -17 -16 -35 -11 -17 -23 -27 -26 -22
89
+ -4 6 -2 13 4 17 6 4 8 11 4 16 -3 5 -10 6 -16 3 -7 -4 -8 -2 -4 5 4 6 11 9 16
90
+ 6 5 -3 11 -1 14 4 3 5 -3 11 -14 14 -10 3 -21 0 -23 -7 -2 -6 -8 -8 -12 -4 -9
91
+ 8 2 28 16 28 6 0 20 -5 32 -11z m-882 -17 c-7 -2 -18 1 -23 6 -8 8 -4 9 13 5
92
+ 13 -4 18 -8 10 -11z m-506 -11 c-8 -14 -25 -14 -25 0 0 5 5 7 10 4 6 -3 10 -1
93
+ 10 6 0 7 3 10 6 6 3 -3 3 -10 -1 -16z m1758 -6 c-10 -13 -22 -25 -27 -25 -9 0
94
+ 11 29 29 42 17 13 17 9 -2 -17z m-302 -55 c-8 -4 -11 -15 -8 -25 4 -9 3 -14
95
+ -3 -10 -14 9 -12 42 3 48 18 6 24 -3 8 -13z m-34 -6 c-3 -3 -12 -4 -19 -1 -8
96
+ 3 -5 6 6 6 11 1 17 -2 13 -5z m153 -14 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11 10
97
+ -3 6 -1 10 4 10 6 0 11 -4 11 -10z m-60 -20 c12 -7 10 -9 -8 -7 -12 0 -22 5
98
+ -22 9 0 11 12 10 30 -2z m40 0 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11 10 -3 6 -1
99
+ 10 4 10 6 0 11 -4 11 -10z m30 -20 c0 -5 -4 -10 -10 -10 -5 0 -10 5 -10 10 0
100
+ 6 5 10 10 10 6 0 10 -4 10 -10z m-44 -37 c-10 -10 -19 5 -10 18 6 11 8 11 12
101
+ 0 2 -7 1 -15 -2 -18z m54 2 c-14 -17 -30 -20 -30 -4 0 5 5 7 10 4 6 -3 10 -1
102
+ 10 4 0 6 5 11 11 11 8 0 8 -5 -1 -15z m-84 -40 c17 -16 14 -18 -10 -9 -9 3
103
+ -16 10 -16 15 0 13 9 11 26 -6z m-562 -350 c8 -19 46 -68 83 -107 66 -70 183
104
+ -218 183 -231 0 -4 -40 -7 -90 -7 l-89 0 -27 48 c-15 26 -64 109 -110 184
105
+ l-83 137 57 4 c31 2 58 4 59 5 2 1 9 -14 17 -33z"/>
106
+ <path d="M2768 3533 c7 -3 16 -2 19 1 4 3 -2 6 -13 5 -11 0 -14 -3 -6 -6z"/>
107
+ <path d="M2808 3533 c6 -2 18 -2 25 0 6 3 1 5 -13 5 -14 0 -19 -2 -12 -5z"/>
108
+ <path d="M2930 3506 c0 -2 8 -10 18 -17 15 -13 16 -12 3 4 -13 16 -21 21 -21
109
+ 13z"/>
110
+ <path d="M2825 2620 c-3 -5 -1 -10 4 -10 6 0 11 5 11 10 0 6 -2 10 -4 10 -3 0
111
+ -8 -4 -11 -10z"/>
112
+ <path d="M2763 2525 c0 -7 6 -11 14 -8 7 3 16 -5 21 -18 9 -23 9 -23 14 -1 3
113
+ 12 3 21 -1 20 -3 -1 -15 3 -27 9 -16 10 -21 9 -21 -2z"/>
114
+ <path d="M2776 2412 c-3 -4 4 -9 15 -9 23 -2 25 3 4 10 -8 4 -16 3 -19 -1z"/>
115
+ <path d="M2861 1837 c-6 -8 -7 -18 -3 -22 4 -5 1 -5 -6 -1 -8 5 -19 -7 -33
116
+ -39 -11 -26 -18 -49 -15 -53 13 -12 55 44 64 86 11 46 10 49 -7 29z"/>
117
+ <path d="M2652 1744 c-29 -28 -42 -50 -42 -68 l0 -27 31 18 c33 19 63 73 57
118
+ 101 -3 13 -13 8 -46 -24z"/>
119
+ <path d="M2772 1618 c-28 -30 -62 -93 -62 -117 0 -20 45 10 73 49 28 40 47
120
+ 100 30 100 -5 0 -23 -15 -41 -32z"/>
121
+ <path d="M2706 1395 c-9 -26 -7 -32 5 -12 6 10 9 21 6 23 -2 3 -7 -2 -11 -11z"/>
122
+ </g>
123
+
124
+ <!-- "Quail" text -->
125
+ <text x="320" y="280" font-family="Verdana, Geneva, sans-serif" font-size="170" font-weight="normal" fill="#CC342D" letter-spacing="2">
126
+ Quail
127
+ </text>
128
+
129
+ </svg>
data/sig/quail.rbs ADDED
@@ -0,0 +1,4 @@
1
+ module Quail
2
+ VERSION: String
3
+ # See the writing guide of rbs: https://github.com/ruby/rbs#guides
4
+ end
metadata ADDED
@@ -0,0 +1,123 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: quail-graphql
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Demetrious Wilson
8
+ bindir: bin
9
+ cert_chain: []
10
+ date: 1980-01-02 00:00:00.000000000 Z
11
+ dependencies:
12
+ - !ruby/object:Gem::Dependency
13
+ name: activerecord
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - ">="
17
+ - !ruby/object:Gem::Version
18
+ version: '7.0'
19
+ type: :runtime
20
+ prerelease: false
21
+ version_requirements: !ruby/object:Gem::Requirement
22
+ requirements:
23
+ - - ">="
24
+ - !ruby/object:Gem::Version
25
+ version: '7.0'
26
+ - !ruby/object:Gem::Dependency
27
+ name: graphql
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - ">="
31
+ - !ruby/object:Gem::Version
32
+ version: '2.0'
33
+ type: :runtime
34
+ prerelease: false
35
+ version_requirements: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - ">="
38
+ - !ruby/object:Gem::Version
39
+ version: '2.0'
40
+ - !ruby/object:Gem::Dependency
41
+ name: railties
42
+ requirement: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: '7.0'
47
+ type: :runtime
48
+ prerelease: false
49
+ version_requirements: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - ">="
52
+ - !ruby/object:Gem::Version
53
+ version: '7.0'
54
+ description: Wraps graphql-ruby with a convention-over-configuration approach. Declare
55
+ resources with a simple DSL and get types, queries, mutations, and subscriptions
56
+ auto-generated from your ActiveRecord models.
57
+ email:
58
+ - demetriouswilson@gmail.com
59
+ executables: []
60
+ extensions: []
61
+ extra_rdoc_files: []
62
+ files:
63
+ - AGENTS.md
64
+ - LICENSE.txt
65
+ - README.md
66
+ - Rakefile
67
+ - lib/generators/quail/channel_generator.rb
68
+ - lib/generators/quail/install_generator.rb
69
+ - lib/generators/quail/resource_generator.rb
70
+ - lib/generators/quail/templates/graphql_channel.rb.tt
71
+ - lib/generators/quail/templates/graphql_channel_custom.rb.tt
72
+ - lib/generators/quail/templates/graphql_controller.rb.tt
73
+ - lib/generators/quail/templates/initializer.rb.tt
74
+ - lib/generators/quail/templates/resource.rb.tt
75
+ - lib/generators/quail/templates/schema.rb.tt
76
+ - lib/quail.rb
77
+ - lib/quail/channel.rb
78
+ - lib/quail/controller_helpers.rb
79
+ - lib/quail/railtie.rb
80
+ - lib/quail/resource.rb
81
+ - lib/quail/resource/dsl.rb
82
+ - lib/quail/resource/mutation_builder.rb
83
+ - lib/quail/resource/mutation_builder/context.rb
84
+ - lib/quail/resource/mutation_builder/resolvers.rb
85
+ - lib/quail/resource/query_builder.rb
86
+ - lib/quail/resource/subscription_builder.rb
87
+ - lib/quail/resource/type_builder.rb
88
+ - lib/quail/resource/type_builder/association_builder.rb
89
+ - lib/quail/resource/type_builder/field_builder.rb
90
+ - lib/quail/schema_builder.rb
91
+ - lib/quail/schema_builder/discovery.rb
92
+ - lib/quail/schema_builder/type_definitions.rb
93
+ - lib/quail/tasks/quail.rake
94
+ - lib/quail/type_map.rb
95
+ - lib/quail/version.rb
96
+ - quail_logo.png
97
+ - quail_logo_new.svg
98
+ - sig/quail.rbs
99
+ homepage: https://quail.taywils.me/
100
+ licenses:
101
+ - MIT
102
+ metadata:
103
+ homepage_uri: https://quail.taywils.me/
104
+ source_code_uri: https://github.com/taywils/quail
105
+ rubygems_mfa_required: 'true'
106
+ rdoc_options: []
107
+ require_paths:
108
+ - lib
109
+ required_ruby_version: !ruby/object:Gem::Requirement
110
+ requirements:
111
+ - - ">="
112
+ - !ruby/object:Gem::Version
113
+ version: 3.2.0
114
+ required_rubygems_version: !ruby/object:Gem::Requirement
115
+ requirements:
116
+ - - ">="
117
+ - !ruby/object:Gem::Version
118
+ version: '0'
119
+ requirements: []
120
+ rubygems_version: 4.0.3
121
+ specification_version: 4
122
+ summary: Rails-first GraphQL with an Alba-inspired declarative DSL
123
+ test_files: []