TypeGenerator::mapAnnotatedObject()   A
last analyzed

Complexity

Conditions 4
Paths 4

Size

Total Lines 23
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 12
dl 0
loc 23
rs 9.8666
c 0
b 0
f 0
cc 4
nc 4
nop 2
1
<?php
2
3
4
namespace TheCodingMachine\GraphQL\Controllers;
5
6
use function get_parent_class;
7
use GraphQL\Type\Definition\ObjectType;
8
use Psr\Container\ContainerInterface;
9
use ReflectionClass;
10
use TheCodingMachine\GraphQL\Controllers\Annotations\Type;
11
use TheCodingMachine\GraphQL\Controllers\Mappers\RecursiveTypeMapperInterface;
12
use TheCodingMachine\GraphQL\Controllers\Types\MutableObjectType;
13
use TheCodingMachine\GraphQL\Controllers\Types\TypeAnnotatedObjectType;
14
15
/**
16
 * This class is in charge of creating Webonix GraphQL types from annotated objects that do not extend the
17
 * Webonix ObjectType class.
18
 */
19
class TypeGenerator
20
{
21
    /**
22
     * @var AnnotationReader
23
     */
24
    private $annotationReader;
25
    /**
26
     * @var FieldsBuilderFactory
27
     */
28
    private $fieldsBuilderFactory;
29
    /**
30
     * @var NamingStrategyInterface
31
     */
32
    private $namingStrategy;
33
    /**
34
     * @var TypeRegistry
35
     */
36
    private $typeRegistry;
37
    /**
38
     * @var ContainerInterface
39
     */
40
    private $container;
41
42
    public function __construct(AnnotationReader $annotationReader,
43
                                FieldsBuilderFactory $fieldsBuilderFactory,
44
                                NamingStrategyInterface $namingStrategy,
45
                                TypeRegistry $typeRegistry,
46
                                ContainerInterface $container)
47
    {
48
        $this->annotationReader = $annotationReader;
49
        $this->fieldsBuilderFactory = $fieldsBuilderFactory;
50
        $this->namingStrategy = $namingStrategy;
51
        $this->typeRegistry = $typeRegistry;
52
        $this->container = $container;
53
    }
54
55
    /**
56
     * @param string $annotatedObjectClassName The FQCN of an object with a Type annotation.
57
     * @param RecursiveTypeMapperInterface $recursiveTypeMapper
58
     * @return MutableObjectType
59
     * @throws \ReflectionException
60
     */
61
    public function mapAnnotatedObject(string $annotatedObjectClassName, RecursiveTypeMapperInterface $recursiveTypeMapper): MutableObjectType
62
    {
63
        $refTypeClass = new \ReflectionClass($annotatedObjectClassName);
64
65
        $typeField = $this->annotationReader->getTypeAnnotation($refTypeClass);
66
67
        if ($typeField === null) {
68
            throw MissingAnnotationException::missingTypeException();
69
        }
70
71
        $typeName = $this->namingStrategy->getOutputTypeName($refTypeClass->getName(), $typeField);
72
73
        if ($this->typeRegistry->hasType($typeName)) {
74
            return $this->typeRegistry->getMutableObjectType($typeName);
75
        }
76
77
        if (!$typeField->isSelfType()) {
78
            $annotatedObject = $this->container->get($annotatedObjectClassName);
79
        } else {
80
            $annotatedObject = null;
81
        }
82
83
        return TypeAnnotatedObjectType::createFromAnnotatedClass($typeName, $typeField->getClass(), $annotatedObject, $this->fieldsBuilderFactory, $recursiveTypeMapper);
84
85
        /*return new ObjectType([
86
            'name' => $typeName,
87
            'fields' => function() use ($annotatedObject, $recursiveTypeMapper, $typeField) {
88
                $parentClass = get_parent_class($typeField->getClass());
89
                $parentType = null;
90
                if ($parentClass !== false) {
91
                    if ($recursiveTypeMapper->canMapClassToType($parentClass)) {
92
                        $parentType = $recursiveTypeMapper->mapClassToType($parentClass, null);
93
                    }
94
                }
95
96
                $fieldProvider = $this->controllerQueryProviderFactory->buildFieldsBuilder($recursiveTypeMapper);
97
                $fields = $fieldProvider->getFields($annotatedObject);
98
                if ($parentType !== null) {
99
                    $fields = $parentType->getFields() + $fields;
100
                }
101
                return $fields;
102
            },
103
            'interfaces' => function() use ($typeField, $recursiveTypeMapper) {
104
                return $recursiveTypeMapper->findInterfaces($typeField->getClass());
105
            }
106
        ]);*/
107
    }
108
109
    /**
110
     * @param object $annotatedObject An object with a ExtendType annotation.
111
     * @param MutableObjectType $type
112
     * @param RecursiveTypeMapperInterface $recursiveTypeMapper
113
     */
114
    public function extendAnnotatedObject($annotatedObject, MutableObjectType $type, RecursiveTypeMapperInterface $recursiveTypeMapper)
115
    {
116
        $refTypeClass = new \ReflectionClass($annotatedObject);
117
118
        $extendTypeAnnotation = $this->annotationReader->getExtendTypeAnnotation($refTypeClass);
119
120
        if ($extendTypeAnnotation === null) {
121
            throw MissingAnnotationException::missingExtendTypeException();
122
        }
123
124
        //$typeName = $this->namingStrategy->getOutputTypeName($refTypeClass->getName(), $extendTypeAnnotation);
125
        $typeName = $type->name;
0 ignored issues
show
Unused Code introduced by
The assignment to $typeName is dead and can be removed.
Loading history...
126
127
        /*if ($this->typeRegistry->hasType($typeName)) {
128
            throw new GraphQLException(sprintf('Tried to extend GraphQL type "%s" that is already stored in the type registry.', $typeName));
129
        }
130
131
        if (!$type instanceof MutableObjectType) {
132
            throw new \RuntimeException('TEMP EXCEPTION');
133
        }*/
134
135
        $type->addFields(function() use ($annotatedObject, $recursiveTypeMapper) {
136
                /*$parentClass = get_parent_class($extendTypeAnnotation->getClass());
137
                $parentType = null;
138
                if ($parentClass !== false) {
139
                    if ($recursiveTypeMapper->canMapClassToType($parentClass)) {
140
                        $parentType = $recursiveTypeMapper->mapClassToType($parentClass, null);
141
                    }
142
                }*/
143
144
                $fieldProvider = $this->fieldsBuilderFactory->buildFieldsBuilder($recursiveTypeMapper);
145
                return $fieldProvider->getFields($annotatedObject);
146
                /*if ($parentType !== null) {
147
                    $fields = $parentType->getFields() + $fields;
148
                }*/
149
            });
150
151
152
//        return new ObjectType([
153
//            'name' => $typeName,
154
//            'fields' => function() use ($annotatedObject, $recursiveTypeMapper, $type) {
155
//                /*$parentClass = get_parent_class($extendTypeAnnotation->getClass());
156
//                $parentType = null;
157
//                if ($parentClass !== false) {
158
//                    if ($recursiveTypeMapper->canMapClassToType($parentClass)) {
159
//                        $parentType = $recursiveTypeMapper->mapClassToType($parentClass, null);
160
//                    }
161
//                }*/
162
//
163
//                $fieldProvider = $this->fieldsBuilderFactory->buildFieldsBuilder($recursiveTypeMapper);
164
//                $fields = $fieldProvider->getFields($annotatedObject);
165
//                /*if ($parentType !== null) {
166
//                    $fields = $parentType->getFields() + $fields;
167
//                }*/
168
//
169
//                $fields = $type->getFields() + $fields;
170
//
171
//                return $fields;
172
//            },
173
//            'interfaces' => function() use ($type) {
174
//                return $type->getInterfaces();
175
//            }
176
//        ]);
177
    }
178
}
179