graphql 0.12.1 → 0.13.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/graphql.rb +31 -41
- data/lib/graphql/argument.rb +23 -21
- data/lib/graphql/base_type.rb +5 -8
- data/lib/graphql/define/assign_argument.rb +5 -2
- data/lib/graphql/define/type_definer.rb +2 -1
- data/lib/graphql/directive.rb +34 -36
- data/lib/graphql/directive/include_directive.rb +3 -7
- data/lib/graphql/directive/skip_directive.rb +3 -7
- data/lib/graphql/enum_type.rb +78 -76
- data/lib/graphql/execution_error.rb +1 -3
- data/lib/graphql/field.rb +99 -95
- data/lib/graphql/input_object_type.rb +49 -47
- data/lib/graphql/interface_type.rb +31 -34
- data/lib/graphql/introspection.rb +19 -18
- data/lib/graphql/introspection/directive_location_enum.rb +8 -0
- data/lib/graphql/introspection/directive_type.rb +1 -3
- data/lib/graphql/introspection/field_type.rb +1 -1
- data/lib/graphql/introspection/fields_field.rb +1 -1
- data/lib/graphql/introspection/introspection_query.rb +1 -3
- data/lib/graphql/introspection/possible_types_field.rb +7 -1
- data/lib/graphql/introspection/schema_field.rb +13 -9
- data/lib/graphql/introspection/type_by_name_field.rb +13 -17
- data/lib/graphql/introspection/typename_field.rb +12 -8
- data/lib/graphql/language.rb +5 -9
- data/lib/graphql/language/lexer.rb +668 -0
- data/lib/graphql/language/lexer.rl +149 -0
- data/lib/graphql/language/parser.rb +842 -116
- data/lib/graphql/language/parser.y +264 -0
- data/lib/graphql/language/token.rb +21 -0
- data/lib/graphql/list_type.rb +33 -31
- data/lib/graphql/non_null_type.rb +33 -31
- data/lib/graphql/object_type.rb +52 -55
- data/lib/graphql/query.rb +83 -80
- data/lib/graphql/query/context.rb +5 -1
- data/lib/graphql/query/directive_resolution.rb +16 -0
- data/lib/graphql/query/executor.rb +3 -3
- data/lib/graphql/query/input_validation_result.rb +17 -15
- data/lib/graphql/query/serial_execution.rb +5 -5
- data/lib/graphql/query/serial_execution/execution_context.rb +4 -3
- data/lib/graphql/query/serial_execution/selection_resolution.rb +19 -21
- data/lib/graphql/query/serial_execution/value_resolution.rb +1 -1
- data/lib/graphql/query/type_resolver.rb +22 -18
- data/lib/graphql/query/variable_validation_error.rb +14 -12
- data/lib/graphql/schema.rb +87 -77
- data/lib/graphql/schema/each_item_validator.rb +16 -12
- data/lib/graphql/schema/field_validator.rb +14 -10
- data/lib/graphql/schema/implementation_validator.rb +26 -22
- data/lib/graphql/schema/middleware_chain.rb +2 -1
- data/lib/graphql/schema/possible_types.rb +34 -0
- data/lib/graphql/schema/printer.rb +122 -120
- data/lib/graphql/schema/type_expression.rb +1 -0
- data/lib/graphql/schema/type_map.rb +3 -10
- data/lib/graphql/schema/type_reducer.rb +65 -81
- data/lib/graphql/schema/type_validator.rb +45 -41
- data/lib/graphql/static_validation.rb +7 -9
- data/lib/graphql/static_validation/all_rules.rb +29 -24
- data/lib/graphql/static_validation/arguments_validator.rb +39 -35
- data/lib/graphql/static_validation/literal_validator.rb +44 -40
- data/lib/graphql/static_validation/message.rb +30 -26
- data/lib/graphql/static_validation/rules/argument_literals_are_compatible.rb +15 -11
- data/lib/graphql/static_validation/rules/arguments_are_defined.rb +14 -10
- data/lib/graphql/static_validation/rules/directives_are_defined.rb +16 -12
- data/lib/graphql/static_validation/rules/directives_are_in_valid_locations.rb +59 -0
- data/lib/graphql/static_validation/rules/fields_are_defined_on_type.rb +25 -21
- data/lib/graphql/static_validation/rules/fields_have_appropriate_selections.rb +28 -24
- data/lib/graphql/static_validation/rules/fields_will_merge.rb +84 -80
- data/lib/graphql/static_validation/rules/fragment_spreads_are_possible.rb +49 -43
- data/lib/graphql/static_validation/rules/fragment_types_exist.rb +22 -17
- data/lib/graphql/static_validation/rules/fragments_are_finite.rb +19 -15
- data/lib/graphql/static_validation/rules/fragments_are_on_composite_types.rb +25 -20
- data/lib/graphql/static_validation/rules/fragments_are_used.rb +36 -23
- data/lib/graphql/static_validation/rules/required_arguments_are_present.rb +29 -25
- data/lib/graphql/static_validation/rules/variable_default_values_are_correctly_typed.rb +21 -17
- data/lib/graphql/static_validation/rules/variable_usages_are_allowed.rb +79 -70
- data/lib/graphql/static_validation/rules/variables_are_input_types.rb +24 -20
- data/lib/graphql/static_validation/rules/variables_are_used_and_defined.rb +122 -119
- data/lib/graphql/static_validation/type_stack.rb +138 -129
- data/lib/graphql/static_validation/validator.rb +29 -25
- data/lib/graphql/type_kinds.rb +42 -40
- data/lib/graphql/union_type.rb +22 -16
- data/lib/graphql/version.rb +1 -1
- data/readme.md +12 -27
- data/spec/graphql/base_type_spec.rb +3 -3
- data/spec/graphql/directive_spec.rb +10 -18
- data/spec/graphql/enum_type_spec.rb +7 -7
- data/spec/graphql/execution_error_spec.rb +1 -1
- data/spec/graphql/field_spec.rb +14 -13
- data/spec/graphql/id_type_spec.rb +6 -6
- data/spec/graphql/input_object_type_spec.rb +39 -39
- data/spec/graphql/interface_type_spec.rb +16 -32
- data/spec/graphql/introspection/directive_type_spec.rb +5 -9
- data/spec/graphql/introspection/input_value_type_spec.rb +10 -4
- data/spec/graphql/introspection/introspection_query_spec.rb +2 -2
- data/spec/graphql/introspection/schema_type_spec.rb +2 -2
- data/spec/graphql/introspection/type_type_spec.rb +34 -6
- data/spec/graphql/language/parser_spec.rb +299 -105
- data/spec/graphql/language/visitor_spec.rb +4 -4
- data/spec/graphql/list_type_spec.rb +11 -11
- data/spec/graphql/object_type_spec.rb +10 -10
- data/spec/graphql/query/arguments_spec.rb +7 -7
- data/spec/graphql/query/context_spec.rb +11 -3
- data/spec/graphql/query/executor_spec.rb +26 -19
- data/spec/graphql/query/serial_execution/execution_context_spec.rb +6 -6
- data/spec/graphql/query/serial_execution/value_resolution_spec.rb +2 -2
- data/spec/graphql/query/type_resolver_spec.rb +3 -3
- data/spec/graphql/query_spec.rb +6 -38
- data/spec/graphql/scalar_type_spec.rb +28 -19
- data/spec/graphql/schema/field_validator_spec.rb +1 -1
- data/spec/graphql/schema/middleware_chain_spec.rb +12 -1
- data/spec/graphql/schema/printer_spec.rb +12 -4
- data/spec/graphql/schema/rescue_middleware_spec.rb +1 -1
- data/spec/graphql/schema/type_expression_spec.rb +2 -2
- data/spec/graphql/schema/type_reducer_spec.rb +21 -36
- data/spec/graphql/schema/type_validator_spec.rb +9 -9
- data/spec/graphql/schema_spec.rb +1 -1
- data/spec/graphql/static_validation/rules/argument_literals_are_compatible_spec.rb +4 -4
- data/spec/graphql/static_validation/rules/arguments_are_defined_spec.rb +4 -4
- data/spec/graphql/static_validation/rules/directives_are_defined_spec.rb +5 -5
- data/spec/graphql/static_validation/rules/directives_are_in_valid_locations_spec.rb +39 -0
- data/spec/graphql/static_validation/rules/fields_are_defined_on_type_spec.rb +5 -5
- data/spec/graphql/static_validation/rules/fields_have_appropriate_selections_spec.rb +4 -4
- data/spec/graphql/static_validation/rules/fields_will_merge_spec.rb +2 -2
- data/spec/graphql/static_validation/rules/fragment_spreads_are_possible_spec.rb +1 -1
- data/spec/graphql/static_validation/rules/fragment_types_exist_spec.rb +2 -2
- data/spec/graphql/static_validation/rules/fragments_are_finite_spec.rb +2 -2
- data/spec/graphql/static_validation/rules/fragments_are_on_composite_types_spec.rb +2 -2
- data/spec/graphql/static_validation/rules/fragments_are_used_spec.rb +3 -3
- data/spec/graphql/static_validation/rules/required_arguments_are_present_spec.rb +3 -3
- data/spec/graphql/static_validation/rules/variable_default_values_are_correctly_typed_spec.rb +5 -5
- data/spec/graphql/static_validation/rules/variable_usages_are_allowed_spec.rb +3 -1
- data/spec/graphql/static_validation/rules/variables_are_input_types_spec.rb +4 -4
- data/spec/graphql/static_validation/rules/variables_are_used_and_defined_spec.rb +3 -3
- data/spec/graphql/static_validation/type_stack_spec.rb +3 -2
- data/spec/graphql/static_validation/validator_spec.rb +26 -6
- data/spec/graphql/union_type_spec.rb +5 -4
- data/spec/spec_helper.rb +2 -5
- data/spec/support/dairy_app.rb +30 -9
- data/spec/support/dairy_data.rb +1 -1
- data/spec/support/star_wars_data.rb +26 -26
- data/spec/support/star_wars_schema.rb +1 -1
- metadata +40 -21
- data/lib/graphql/language/transform.rb +0 -113
- data/lib/graphql/query/directive_chain.rb +0 -44
- data/lib/graphql/repl.rb +0 -27
- data/spec/graphql/language/transform_spec.rb +0 -156
@@ -1,27 +1,27 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::ID_TYPE do
|
4
4
|
let(:result) { DummySchema.execute(query_string)}
|
5
5
|
|
6
|
-
describe
|
6
|
+
describe "coercion for int inputs" do
|
7
7
|
let(:query_string) { %|query getMilk { cow: milk(id: 1) { id } }| }
|
8
8
|
|
9
|
-
it
|
9
|
+
it "coerces IDs from ints and serializes as strings" do
|
10
10
|
expected = {"data" => {"cow" => {"id" => "1"}}}
|
11
11
|
assert_equal(expected, result)
|
12
12
|
end
|
13
13
|
end
|
14
14
|
|
15
|
-
describe
|
15
|
+
describe "coercion for string inputs" do
|
16
16
|
let(:query_string) { %|query getMilk { cow: milk(id: "1") { id } }| }
|
17
17
|
|
18
|
-
it
|
18
|
+
it "coerces IDs from strings and serializes as strings" do
|
19
19
|
expected = {"data" => {"cow" => {"id" => "1"}}}
|
20
20
|
assert_equal(expected, result)
|
21
21
|
end
|
22
22
|
end
|
23
23
|
|
24
|
-
describe
|
24
|
+
describe "coercion for other types" do
|
25
25
|
let(:query_string) { %|query getMilk { cow: milk(id: 1.0) { id } }| }
|
26
26
|
|
27
27
|
it "doesn't allow other types" do
|
@@ -1,12 +1,12 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::InputObjectType do
|
4
4
|
let(:input_object) { DairyProductInputType }
|
5
|
-
it
|
5
|
+
it "has a description" do
|
6
6
|
assert(input_object.description)
|
7
7
|
end
|
8
8
|
|
9
|
-
it
|
9
|
+
it "has input fields" do
|
10
10
|
assert(DairyProductInputType.input_fields["fatContent"])
|
11
11
|
end
|
12
12
|
|
@@ -16,7 +16,7 @@ describe GraphQL::InputObjectType do
|
|
16
16
|
assert DairyProductInputType.valid_input?(values_obj)
|
17
17
|
end
|
18
18
|
|
19
|
-
describe
|
19
|
+
describe "validate_input with non-enumerable input" do
|
20
20
|
it "returns a valid result for MinimumInputObject" do
|
21
21
|
result = DairyProductInputType.validate_input(MinimumInputObject.new({"source" => "COW", "fatContent" => 0.4}))
|
22
22
|
assert(result.valid?)
|
@@ -29,86 +29,86 @@ describe GraphQL::InputObjectType do
|
|
29
29
|
end
|
30
30
|
end
|
31
31
|
|
32
|
-
describe
|
33
|
-
describe
|
32
|
+
describe "validate_input with enumerable input" do
|
33
|
+
describe "with good input" do
|
34
34
|
let(:input) do
|
35
35
|
{
|
36
|
-
|
37
|
-
|
36
|
+
"source" => "COW",
|
37
|
+
"fatContent" => 0.4
|
38
38
|
}
|
39
39
|
end
|
40
40
|
let(:result) { DairyProductInputType.validate_input(input) }
|
41
41
|
|
42
|
-
it
|
42
|
+
it "returns a valid result" do
|
43
43
|
assert(result.valid?)
|
44
44
|
end
|
45
45
|
end
|
46
46
|
|
47
|
-
describe
|
48
|
-
let(:result) { DairyProductInputType.validate_input(
|
47
|
+
describe "with bad enum and float" do
|
48
|
+
let(:result) { DairyProductInputType.validate_input("source" => "KOALA", "fatContent" => "bad_num") }
|
49
49
|
|
50
|
-
it
|
50
|
+
it "returns an invalid result" do
|
51
51
|
assert(!result.valid?)
|
52
52
|
end
|
53
53
|
|
54
|
-
it
|
55
|
-
paths = result.problems.map { |p| p[
|
56
|
-
assert(paths.include?([
|
57
|
-
assert(paths.include?([
|
54
|
+
it "has problems with correct paths" do
|
55
|
+
paths = result.problems.map { |p| p["path"] }
|
56
|
+
assert(paths.include?(["source"]))
|
57
|
+
assert(paths.include?(["fatContent"]))
|
58
58
|
end
|
59
59
|
|
60
|
-
it
|
61
|
-
expected = DairyAnimalEnum.validate_input(
|
60
|
+
it "has correct problem explanation" do
|
61
|
+
expected = DairyAnimalEnum.validate_input("KOALA").problems[0]["explanation"]
|
62
62
|
|
63
|
-
source_problem = result.problems.detect { |p| p[
|
64
|
-
actual = source_problem[
|
63
|
+
source_problem = result.problems.detect { |p| p["path"] == ["source"] }
|
64
|
+
actual = source_problem["explanation"]
|
65
65
|
|
66
66
|
assert_equal(expected, actual)
|
67
67
|
end
|
68
68
|
end
|
69
69
|
|
70
|
-
describe
|
71
|
-
let(:result) { DairyProductInputType.validate_input(
|
70
|
+
describe "with extra argument" do
|
71
|
+
let(:result) { DairyProductInputType.validate_input("source" => "COW", "fatContent" => 0.4, "isDelicious" => false) }
|
72
72
|
|
73
|
-
it
|
73
|
+
it "returns an invalid result" do
|
74
74
|
assert(!result.valid?)
|
75
75
|
end
|
76
76
|
|
77
|
-
it
|
78
|
-
paths = result.problems.map { |p| p[
|
79
|
-
assert_equal(paths, [[
|
77
|
+
it "has problem with correct path" do
|
78
|
+
paths = result.problems.map { |p| p["path"] }
|
79
|
+
assert_equal(paths, [["isDelicious"]])
|
80
80
|
end
|
81
81
|
|
82
|
-
it
|
83
|
-
assert(result.problems[0][
|
82
|
+
it "has correct problem explanation" do
|
83
|
+
assert(result.problems[0]["explanation"].include?("Field is not defined"))
|
84
84
|
end
|
85
85
|
end
|
86
86
|
|
87
|
-
describe
|
87
|
+
describe "list with one invalid element" do
|
88
88
|
let(:list_type) { GraphQL::ListType.new(of_type: DairyProductInputType) }
|
89
89
|
let(:result) do
|
90
90
|
list_type.validate_input([
|
91
|
-
{
|
92
|
-
{
|
91
|
+
{ "source" => "COW", "fatContent" => 0.4 },
|
92
|
+
{ "source" => "KOALA", "fatContent" => 0.4 }
|
93
93
|
])
|
94
94
|
end
|
95
95
|
|
96
|
-
it
|
96
|
+
it "returns an invalid result" do
|
97
97
|
assert(!result.valid?)
|
98
98
|
end
|
99
99
|
|
100
|
-
it
|
100
|
+
it "has one problem" do
|
101
101
|
assert_equal(result.problems.length, 1)
|
102
102
|
end
|
103
103
|
|
104
|
-
it
|
105
|
-
path = result.problems[0][
|
106
|
-
assert_equal(path, [1,
|
104
|
+
it "has problem with correct path" do
|
105
|
+
path = result.problems[0]["path"]
|
106
|
+
assert_equal(path, [1, "source"])
|
107
107
|
end
|
108
108
|
|
109
|
-
it
|
110
|
-
expected = DairyAnimalEnum.validate_input(
|
111
|
-
actual = result.problems[0][
|
109
|
+
it "has problem with correct explanation" do
|
110
|
+
expected = DairyAnimalEnum.validate_input("KOALA").problems[0]["explanation"]
|
111
|
+
actual = result.problems[0]["explanation"]
|
112
112
|
assert_equal(expected, actual)
|
113
113
|
end
|
114
114
|
end
|
@@ -1,56 +1,40 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::InterfaceType do
|
4
4
|
let(:interface) { EdibleInterface }
|
5
|
-
|
6
|
-
assert_equal([CheeseType, MilkType, HoneyType], interface.possible_types)
|
7
|
-
end
|
5
|
+
let(:dummy_query_context) { OpenStruct.new(schema: DummySchema) }
|
8
6
|
|
9
|
-
it
|
10
|
-
assert_equal(CheeseType,
|
11
|
-
assert_equal(MilkType, interface.resolve_type(MILKS.values.first))
|
7
|
+
it "has possible types" do
|
8
|
+
assert_equal([CheeseType, HoneyType, MilkType], DummySchema.possible_types(interface))
|
12
9
|
end
|
13
10
|
|
14
|
-
it
|
15
|
-
|
16
|
-
|
17
|
-
type = GraphQL::ObjectType.define do
|
18
|
-
interfaces [iface]
|
19
|
-
end
|
20
|
-
assert_equal([type], iface.possible_types)
|
21
|
-
|
22
|
-
type.interfaces = []
|
23
|
-
assert_equal([], iface.possible_types)
|
24
|
-
|
25
|
-
type.interfaces = [iface]
|
26
|
-
assert_equal([type], iface.possible_types)
|
27
|
-
|
28
|
-
type.interfaces = [iface]
|
29
|
-
assert_equal([type], iface.possible_types)
|
11
|
+
it "resolves types for objects" do
|
12
|
+
assert_equal(CheeseType, interface.resolve_type(CHEESES.values.first, dummy_query_context))
|
13
|
+
assert_equal(MilkType, interface.resolve_type(MILKS.values.first, dummy_query_context))
|
30
14
|
end
|
31
15
|
|
32
|
-
describe
|
33
|
-
let(:result) { DummySchema.execute(query_string,
|
16
|
+
describe "query evaluation" do
|
17
|
+
let(:result) { DummySchema.execute(query_string, variables: {"cheeseId" => 2})}
|
34
18
|
let(:query_string) {%|
|
35
19
|
query fav {
|
36
20
|
favoriteEdible { fatContent }
|
37
21
|
}
|
38
22
|
|}
|
39
|
-
it
|
23
|
+
it "gets fields from the type for the given object" do
|
40
24
|
expected = {"data"=>{"favoriteEdible"=>{"fatContent"=>0.04}}}
|
41
25
|
assert_equal(expected, result)
|
42
26
|
end
|
43
27
|
end
|
44
28
|
|
45
|
-
describe
|
46
|
-
let(:result) { DummySchema.execute(query_string,
|
29
|
+
describe "mergable query evaluation" do
|
30
|
+
let(:result) { DummySchema.execute(query_string, variables: {"cheeseId" => 2})}
|
47
31
|
let(:query_string) {%|
|
48
32
|
query fav {
|
49
33
|
favoriteEdible { fatContent }
|
50
34
|
favoriteEdible { origin }
|
51
35
|
}
|
52
36
|
|}
|
53
|
-
it
|
37
|
+
it "gets fields from the type for the given object" do
|
54
38
|
expected = {"data"=>{"favoriteEdible"=>{"fatContent"=>0.04, "origin"=>"Antiquity"}}}
|
55
39
|
assert_equal(expected, result)
|
56
40
|
end
|
@@ -59,14 +43,14 @@ describe GraphQL::InterfaceType do
|
|
59
43
|
describe '#resolve_type' do
|
60
44
|
let(:interface) {
|
61
45
|
GraphQL::InterfaceType.define do
|
62
|
-
resolve_type -> (object) {
|
46
|
+
resolve_type -> (object, ctx) {
|
63
47
|
:custom_resolve
|
64
48
|
}
|
65
49
|
end
|
66
50
|
}
|
67
51
|
|
68
|
-
it
|
69
|
-
assert_equal(interface.resolve_type(123), :custom_resolve)
|
52
|
+
it "can be overriden in the definition" do
|
53
|
+
assert_equal(interface.resolve_type(123, nil), :custom_resolve)
|
70
54
|
end
|
71
55
|
end
|
72
56
|
end
|
@@ -1,16 +1,16 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::Introspection::DirectiveType do
|
4
4
|
let(:query_string) {%|
|
5
5
|
query getDirectives {
|
6
6
|
__schema {
|
7
|
-
directives { name, args { name, type { name, ofType { name } } },
|
7
|
+
directives { name, args { name, type { name, ofType { name } } }, locations }
|
8
8
|
}
|
9
9
|
}
|
10
10
|
|}
|
11
11
|
let(:result) { DummySchema.execute(query_string) }
|
12
12
|
|
13
|
-
it
|
13
|
+
it "shows directive info " do
|
14
14
|
expected = { "data" => {
|
15
15
|
"__schema" => {
|
16
16
|
"directives" => [
|
@@ -19,18 +19,14 @@ describe GraphQL::Introspection::DirectiveType do
|
|
19
19
|
"args" => [
|
20
20
|
{"name"=>"if", "type"=>{"name"=>"Non-Null", "ofType"=>{"name"=>"Boolean"}}}
|
21
21
|
],
|
22
|
-
"
|
23
|
-
"onFragment" => true,
|
24
|
-
"onOperation" => false,
|
22
|
+
"locations"=>["FIELD", "FRAGMENT_SPREAD", "INLINE_FRAGMENT"],
|
25
23
|
},
|
26
24
|
{
|
27
25
|
"name" => "include",
|
28
26
|
"args" => [
|
29
27
|
{"name"=>"if", "type"=>{"name"=>"Non-Null", "ofType"=>{"name"=>"Boolean"}}}
|
30
28
|
],
|
31
|
-
"
|
32
|
-
"onFragment" => true,
|
33
|
-
"onOperation" => false,
|
29
|
+
"locations"=>["FIELD", "FRAGMENT_SPREAD", "INLINE_FRAGMENT"],
|
34
30
|
},
|
35
31
|
]
|
36
32
|
}
|
@@ -12,22 +12,28 @@ describe GraphQL::Introspection::InputValueType do
|
|
12
12
|
name,
|
13
13
|
type { name },
|
14
14
|
defaultValue
|
15
|
+
description
|
15
16
|
}
|
16
17
|
}
|
17
18
|
}
|
18
19
|
|}
|
19
20
|
let(:result) { DummySchema.execute(query_string)}
|
20
21
|
|
21
|
-
it
|
22
|
+
it "exposes metadata about input objects, giving extra quotes for strings" do
|
22
23
|
expected = { "data" => {
|
23
24
|
"__type" => {
|
24
25
|
"name"=>"DairyProductInput",
|
25
26
|
"description"=>"Properties for finding a dairy product",
|
26
27
|
"kind"=>"INPUT_OBJECT",
|
27
28
|
"inputFields"=>[
|
28
|
-
{"name"=>"source", "type"=>{ "name" => "Non-Null"}, "defaultValue"=>nil
|
29
|
-
|
30
|
-
{"name"=>"
|
29
|
+
{"name"=>"source", "type"=>{ "name" => "Non-Null"}, "defaultValue"=>nil,
|
30
|
+
"description" => "Where it came from"},
|
31
|
+
{"name"=>"originDairy", "type"=>{ "name" => "String"}, "defaultValue"=>"\"Sugar Hollow Dairy\"",
|
32
|
+
"description" => "Dairy which produced it"},
|
33
|
+
{"name"=>"fatContent", "type"=>{ "name" => "Float"}, "defaultValue"=>"0.3",
|
34
|
+
"description" => "How much fat it has"},
|
35
|
+
{"name"=>"organic", "type"=>{ "name" => "Boolean"}, "defaultValue"=>"false",
|
36
|
+
"description" => nil}
|
31
37
|
]
|
32
38
|
}
|
33
39
|
}}
|
@@ -1,10 +1,10 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe "GraphQL::Introspection::INTROSPECTION_QUERY" do
|
4
4
|
let(:query_string) { GraphQL::Introspection::INTROSPECTION_QUERY }
|
5
5
|
let(:result) { DummySchema.execute(query_string) }
|
6
6
|
|
7
|
-
it
|
7
|
+
it "runs" do
|
8
8
|
assert(result["data"])
|
9
9
|
end
|
10
10
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::Introspection::SchemaType do
|
4
4
|
let(:query_string) {%|
|
@@ -12,7 +12,7 @@ describe GraphQL::Introspection::SchemaType do
|
|
12
12
|
|}
|
13
13
|
let(:result) { DummySchema.execute(query_string) }
|
14
14
|
|
15
|
-
it
|
15
|
+
it "exposes the schema" do
|
16
16
|
expected = { "data" => {
|
17
17
|
"__schema" => {
|
18
18
|
"types" => DummySchema.types.values.map { |t| t.name.nil? ? (p t; raise("no name for #{t}")) : {"name" => t.name} },
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe GraphQL::Introspection::TypeType do
|
4
4
|
let(:query_string) {%|
|
@@ -12,8 +12,10 @@ describe GraphQL::Introspection::TypeType do
|
|
12
12
|
|}
|
13
13
|
let(:result) { DummySchema.execute(query_string, context: {}, variables: {"cheeseId" => 2}) }
|
14
14
|
let(:cheese_fields) {[
|
15
|
+
{"name"=>"deeplyNullableCheese", "isDeprecated"=>false, "type"=>{"name"=>"Cheese", "ofType"=>nil}},
|
15
16
|
{"name"=>"flavor", "isDeprecated" => false, "type" => { "name" => "Non-Null", "ofType" => { "name" => "String"}}},
|
16
17
|
{"name"=>"id", "isDeprecated" => false, "type" => { "name" => "Non-Null", "ofType" => { "name" => "Int"}}},
|
18
|
+
{"name"=>"nullableCheese", "isDeprecated"=>false, "type"=>{"name"=>"Cheese", "ofType"=>nil}},
|
17
19
|
{"name"=>"origin", "isDeprecated" => false, "type" => { "name" => "Non-Null", "ofType" => { "name" => "String"}}},
|
18
20
|
{"name"=>"similarCheese", "isDeprecated"=>false, "type"=>{"name"=>"Cheese", "ofType"=>nil}},
|
19
21
|
{"name"=>"source", "isDeprecated" => false, "type" => { "name" => "Non-Null", "ofType" => { "name" => "DairyAnimal"}}},
|
@@ -24,7 +26,7 @@ describe GraphQL::Introspection::TypeType do
|
|
24
26
|
{"name"=>"GOAT", "isDeprecated"=> false },
|
25
27
|
{"name"=>"SHEEP", "isDeprecated"=> false },
|
26
28
|
]}
|
27
|
-
it
|
29
|
+
it "exposes metadata about types" do
|
28
30
|
expected = {"data"=> {
|
29
31
|
"cheeseType" => {
|
30
32
|
"name"=> "Cheese",
|
@@ -57,7 +59,7 @@ describe GraphQL::Introspection::TypeType do
|
|
57
59
|
"animalProduct" => {
|
58
60
|
"name"=>"AnimalProduct",
|
59
61
|
"kind"=>"INTERFACE",
|
60
|
-
"possibleTypes"=>[{"name"=>"Cheese"}, {"name"=>"
|
62
|
+
"possibleTypes"=>[{"name"=>"Cheese"}, {"name"=>"Honey"}, {"name"=>"Milk"}],
|
61
63
|
"fields"=>[
|
62
64
|
{"name"=>"source"},
|
63
65
|
]
|
@@ -66,7 +68,7 @@ describe GraphQL::Introspection::TypeType do
|
|
66
68
|
assert_equal(expected, result)
|
67
69
|
end
|
68
70
|
|
69
|
-
describe
|
71
|
+
describe "deprecated fields" do
|
70
72
|
let(:query_string) {%|
|
71
73
|
query introspectionQuery {
|
72
74
|
cheeseType: __type(name: "Cheese") { name, kind, fields(includeDeprecated: true) { name, isDeprecated, type { name, ofType { name } } } }
|
@@ -74,8 +76,9 @@ describe GraphQL::Introspection::TypeType do
|
|
74
76
|
}
|
75
77
|
|}
|
76
78
|
let(:deprecated_fields) { {"name"=>"fatContent", "isDeprecated"=>true, "type"=>{"name"=>"Non-Null", "ofType"=>{"name"=>"Float"}}} }
|
77
|
-
|
78
|
-
|
79
|
+
|
80
|
+
it "can expose deprecated fields" do
|
81
|
+
new_cheese_fields = ([deprecated_fields] + cheese_fields).sort_by { |f| f["name"] }
|
79
82
|
expected = { "data" => {
|
80
83
|
"cheeseType" => {
|
81
84
|
"name"=> "Cheese",
|
@@ -90,5 +93,30 @@ describe GraphQL::Introspection::TypeType do
|
|
90
93
|
}}
|
91
94
|
assert_equal(expected, result)
|
92
95
|
end
|
96
|
+
|
97
|
+
describe "input objects" do
|
98
|
+
let(:query_string) {%|
|
99
|
+
query introspectionQuery {
|
100
|
+
__type(name: "DairyProductInput") { name, description, kind, inputFields { name, type { name }, defaultValue } }
|
101
|
+
}
|
102
|
+
|}
|
103
|
+
|
104
|
+
it "exposes metadata about input objects" do
|
105
|
+
expected = { "data" => {
|
106
|
+
"__type" => {
|
107
|
+
"name"=>"DairyProductInput",
|
108
|
+
"description"=>"Properties for finding a dairy product",
|
109
|
+
"kind"=>"INPUT_OBJECT",
|
110
|
+
"inputFields"=>[
|
111
|
+
{"name"=>"source", "type"=>{ "name" => "Non-Null"}, "defaultValue"=>nil},
|
112
|
+
{"name"=>"originDairy", "type"=>{"name"=>"String"}, "defaultValue"=>"\"Sugar Hollow Dairy\""},
|
113
|
+
{"name"=>"fatContent", "type"=>{ "name" => "Float"}, "defaultValue"=>"0.3"},
|
114
|
+
{"name"=>"organic", "type"=>{ "name" => "Boolean"}, "defaultValue"=>"false"},
|
115
|
+
]
|
116
|
+
}
|
117
|
+
}}
|
118
|
+
assert_equal(expected, result)
|
119
|
+
end
|
120
|
+
end
|
93
121
|
end
|
94
122
|
end
|