mirror of
https://github.com/retailcrm/graphql-php.git
synced 2024-11-21 20:36:05 +03:00
TASK: Allow Schema extensions
This commit is contained in:
parent
0c33cfa88f
commit
b1cd086177
@ -69,6 +69,9 @@ class NodeKind
|
||||
|
||||
const DIRECTIVE_DEFINITION = 'DirectiveDefinition';
|
||||
|
||||
// Type System Extensions
|
||||
const SCHEMA_EXTENSION = 'SchemaExtension';
|
||||
|
||||
/** @var string[] */
|
||||
public static $classMap = [
|
||||
self::NAME => NameNode::class,
|
||||
|
17
src/Language/AST/SchemaTypeExtensionNode.php
Normal file
17
src/Language/AST/SchemaTypeExtensionNode.php
Normal file
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace GraphQL\Language\AST;
|
||||
|
||||
class SchemaTypeExtensionNode extends Node implements TypeExtensionNode
|
||||
{
|
||||
/** @var string */
|
||||
public $kind = NodeKind::SCHEMA_EXTENSION;
|
||||
|
||||
/** @var DirectiveNode[]|null */
|
||||
public $directives;
|
||||
|
||||
/** @var OperationTypeDefinitionNode[]|null */
|
||||
public $operationTypes;
|
||||
}
|
@ -44,6 +44,7 @@ use GraphQL\Language\AST\OperationTypeDefinitionNode;
|
||||
use GraphQL\Language\AST\ScalarTypeDefinitionNode;
|
||||
use GraphQL\Language\AST\ScalarTypeExtensionNode;
|
||||
use GraphQL\Language\AST\SchemaDefinitionNode;
|
||||
use GraphQL\Language\AST\SchemaTypeExtensionNode;
|
||||
use GraphQL\Language\AST\SelectionSetNode;
|
||||
use GraphQL\Language\AST\StringValueNode;
|
||||
use GraphQL\Language\AST\TypeExtensionNode;
|
||||
@ -1446,6 +1447,8 @@ class Parser
|
||||
|
||||
if ($keywordToken->kind === Token::NAME) {
|
||||
switch ($keywordToken->value) {
|
||||
case 'schema':
|
||||
return $this->parseSchemaTypeExtension();
|
||||
case 'scalar':
|
||||
return $this->parseScalarTypeExtension();
|
||||
case 'type':
|
||||
@ -1464,6 +1467,33 @@ class Parser
|
||||
throw $this->unexpected($keywordToken);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return SchemaTypeExtensionNode
|
||||
* @throws SyntaxError
|
||||
*/
|
||||
private function parseSchemaTypeExtension()
|
||||
{
|
||||
$start = $this->lexer->token;
|
||||
$this->expectKeyword('extend');
|
||||
$this->expectKeyword('schema');
|
||||
$directives = $this->parseDirectives(true);
|
||||
$operationTypes = $this->peek(Token::BRACE_L)
|
||||
? $this->many(
|
||||
Token::BRACE_L,
|
||||
[$this, 'parseOperationTypeDefinition'],
|
||||
Token::BRACE_R
|
||||
) : [];
|
||||
if (count($directives) === 0 && count($operationTypes) === 0) {
|
||||
$this->unexpected();
|
||||
}
|
||||
|
||||
return new SchemaTypeExtensionNode([
|
||||
'directives' => $directives,
|
||||
'operationTypes' => $operationTypes,
|
||||
'loc' => $this->loc($start)
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return ScalarTypeExtensionNode
|
||||
* @throws SyntaxError
|
||||
|
@ -41,6 +41,7 @@ use GraphQL\Language\AST\OperationTypeDefinitionNode;
|
||||
use GraphQL\Language\AST\ScalarTypeDefinitionNode;
|
||||
use GraphQL\Language\AST\ScalarTypeExtensionNode;
|
||||
use GraphQL\Language\AST\SchemaDefinitionNode;
|
||||
use GraphQL\Language\AST\SchemaTypeExtensionNode;
|
||||
use GraphQL\Language\AST\SelectionSetNode;
|
||||
use GraphQL\Language\AST\StringValueNode;
|
||||
use GraphQL\Language\AST\UnionTypeDefinitionNode;
|
||||
@ -335,6 +336,17 @@ class Printer
|
||||
);
|
||||
}),
|
||||
|
||||
NodeKind::SCHEMA_EXTENSION => function (SchemaTypeExtensionNode $def) {
|
||||
return $this->join(
|
||||
[
|
||||
'extend schema',
|
||||
$this->join($def->directives, ' '),
|
||||
$this->block($def->operationTypes)
|
||||
],
|
||||
' '
|
||||
);
|
||||
},
|
||||
|
||||
NodeKind::SCALAR_TYPE_EXTENSION => function (ScalarTypeExtensionNode $def) {
|
||||
return $this->join(
|
||||
[
|
||||
|
@ -165,6 +165,8 @@ class Visitor
|
||||
NodeKind::INPUT_OBJECT_TYPE_EXTENSION => ['name', 'directives', 'fields'],
|
||||
|
||||
NodeKind::DIRECTIVE_DEFINITION => ['description', 'name', 'arguments', 'locations'],
|
||||
|
||||
NodeKind::SCHEMA_EXTENSION => ['directives', 'operationTypes']
|
||||
];
|
||||
|
||||
/**
|
||||
|
@ -8,6 +8,7 @@ use GraphQL\Error\Error;
|
||||
use GraphQL\Error\InvariantViolation;
|
||||
use GraphQL\GraphQL;
|
||||
use GraphQL\Language\AST\SchemaDefinitionNode;
|
||||
use GraphQL\Language\AST\SchemaTypeExtensionNode;
|
||||
use GraphQL\Type\Definition\AbstractType;
|
||||
use GraphQL\Type\Definition\Directive;
|
||||
use GraphQL\Type\Definition\InterfaceType;
|
||||
@ -67,6 +68,9 @@ class Schema
|
||||
/** @var InvariantViolation[]|null */
|
||||
private $validationErrors;
|
||||
|
||||
/** @var SchemaTypeExtensionNode[] */
|
||||
public $extensionASTNodes;
|
||||
|
||||
/**
|
||||
* @api
|
||||
* @param mixed[]|SchemaConfig $config
|
||||
@ -111,6 +115,8 @@ class Schema
|
||||
}
|
||||
|
||||
$this->config = $config;
|
||||
$this->extensionASTNodes = $config->extensionASTNodes;
|
||||
|
||||
if ($config->query) {
|
||||
$this->resolvedTypes[$config->query->name] = $config->query;
|
||||
}
|
||||
|
@ -5,6 +5,7 @@ declare(strict_types=1);
|
||||
namespace GraphQL\Type;
|
||||
|
||||
use GraphQL\Language\AST\SchemaDefinitionNode;
|
||||
use GraphQL\Language\AST\SchemaTypeExtensionNode;
|
||||
use GraphQL\Type\Definition\Directive;
|
||||
use GraphQL\Type\Definition\ObjectType;
|
||||
use GraphQL\Type\Definition\Type;
|
||||
@ -51,6 +52,9 @@ class SchemaConfig
|
||||
/** @var bool */
|
||||
public $assumeValid;
|
||||
|
||||
/** @var SchemaTypeExtensionNode[] */
|
||||
public $extensionASTNodes;
|
||||
|
||||
/**
|
||||
* Converts an array of options to instance of SchemaConfig
|
||||
* (or just returns empty config when array is not passed).
|
||||
@ -100,6 +104,10 @@ class SchemaConfig
|
||||
if (isset($options['assumeValid'])) {
|
||||
$config->setAssumeValid((bool) $options['assumeValid']);
|
||||
}
|
||||
|
||||
if (isset($options['extensionASTNodes'])) {
|
||||
$config->setExtensionASTNodes($options['extensionASTNodes']);
|
||||
}
|
||||
}
|
||||
|
||||
return $config;
|
||||
@ -266,4 +274,20 @@ class SchemaConfig
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return SchemaTypeExtensionNode[]
|
||||
*/
|
||||
public function getExtensionASTNodes(): array
|
||||
{
|
||||
return $this->extensionASTNodes;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param SchemaTypeExtensionNode[] $extensionASTNodes
|
||||
*/
|
||||
public function setExtensionASTNodes(array $extensionASTNodes): void
|
||||
{
|
||||
$this->extensionASTNodes = $extensionASTNodes;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user