[toc]
#### 关于输入/输出类型
GraphQL从 Clients 接收数据是通过 字段配制项(fields) 的 参数选项(args) 获取的。
字段(fields)和参数(args)在定义中都需要类型选项(type),但是fields 和 args 的 type 选项的值是不同的,如GraphQL 的 args在概念上输入,而 fields 在概念上输出。
在GraphQL中所有的 types 有两个类型:input 和 output。
* Output types(or field types)are:Scale,Enum,Object,Interface,Union。
* Input types(or arguments types)are:Scale,Enum,InputObject。
显然 NonNull 和 List 类型根据它们内部类型属于上面两种分类。
输入复杂类型在 mutations 是相当有价值的,例如 新增/修改一条数据。
#### 输入对象类型
InputObjectType
GraphQL 为复杂的输入 定义了 InputObjectType,它的定义和 ObjectType 很相似,除了它的 fields 配制没有 args 元素 和 resolve 元素 并且它的类型必须是 input type。
Input Object Type 是 GraphQL\Type\Definition\InputObjectType (或其子类)的实例,它的构造函数接收数组配制参数。
#### 配制项
| 名字 | 类型 | 描述 |
| --- | --- | --- |
| name | `string` | `必填` 输入类型在Schema内的唯一名字 |
| fields | `array` or `callback` returning `array` | `必填` 描述对象字段的数组 (看下面 的详情) |
| description | `string` | 类型的纯文本描述(例如通过GraphQL自动生成文档) |
每个字段都是下面的条目组成的数组
| 名字 | 类型 | 描述 |
| --- | --- | --- |
| name | `string` | `必填` 输入字段的名字 如果没有设置则取数组的键名 |
| type | `Type` | `必填` 输入类型之一的实例 (Scalar, Enum, InputObjectType + 具有 NonNull 和 List修饰的这些类型的组合 |
| description | `string` | 输入类型的纯文本描述(例如通过GraphQL自动生成文档) |
| defaultValue | `scalar` | 这个输入类型的默认值 |
#### 示例
~~~
$filters = new InputObjectType([
'name' => 'StoryFiltersInput',
'fields' => [
'author' => [
'type' => Type::id(),
'description' => 'Only show stories with this author id'
],
'popular' => [
'type' => Type::boolean(),
'description' => 'Only show popular stories (liked by several people)'
],
'tags' => [
'type' => Type::listOf(Type::string()),
'description' => 'Only show stories which contain all of those tags'
]
]
]);
~~~
上面的例子我们定义了自己的输入对象类型,现在我们使用它作为一个字段的参数。
~~~
$queryType = new ObjectType([
'name' => 'Query',
'fields' => [
'stories' => [
'type' => Type::listOf($storyType),
'args' => [
'filters' => [
'type' => Type::nonNull($filters),
'defaultValue' => [
'popular' => true
]
]
],
'resolve' => function($rootValue, $args) {
return DataSource::filterStories($args['filters']);
}
]
]
]);
~~~
(记住,你可以为具有复杂输入的字段定义 一个关联数组的默认值(defaultValue))
然后GraphQL query 可以包含 我们定义的 filters 作为字面值。
~~~
{
stories(filters: {author: "1", popular: false})
}
~~~
或用query variables 的方式作为查询变量
~~~
query($filters: StoryFiltersInput!) {
stories(filters: $filters)
}
~~~
将包含元素filters的对象 和 query字符串查询主体一起传到后台
~~~
$variables = [
'filters' => [
"author" => "1",
"popular" => false
]
];
~~~
后台将$variables作为excute的第5个参数,GraphQL将根据您的 InputObjectType定义验证输入,并将其传递给您的解析器(resolve 或 resolveField)作为参数 $args值的一部分。