Passed
Push — v2 ( b247ab...8c624d )
by Alexander
02:21
created

ResourceFactory::instatiateResource()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 10
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 3

Importance

Changes 0
Metric Value
cc 3
eloc 6
nc 3
nop 3
dl 0
loc 10
ccs 6
cts 6
cp 1
crap 3
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
namespace Flugg\Responder\Resources;
4
5
use Flugg\Responder\Contracts\Resources\ResourceFactory as ResourceFactoryContract;
6
use Flugg\Responder\Contracts\Transformers\TransformerResolver;
7
use Illuminate\Support\Arr;
8
use League\Fractal\Resource\Collection as CollectionResource;
9
use League\Fractal\Resource\Item as ItemResource;
10
use League\Fractal\Resource\NullResource;
11
use League\Fractal\Resource\ResourceInterface;
12
use Traversable;
13
14
/**
15
 * This class is responsible for making Fractal resources from a variety of data types.
16
 *
17
 * @package flugger/laravel-responder
18
 * @author  Alexander Tømmerås <[email protected]>
19
 * @license The MIT License
20
 */
21
class ResourceFactory implements ResourceFactoryContract
22
{
23
    /**
24
     * A service class, used to normalize data.
25
     *
26
     * @var \Flugg\Responder\DataNormalizer
27
     */
28
    protected $normalizer;
29
30
    /**
31
     * A manager class, used to manage transformers.
32
     *
33
     * @var \Flugg\Responder\Contracts\Transformers\TransformerResolver
34
     */
35
    protected $transformerResolver;
36
37
    /**
38
     * Construct the factory class.
39
     *
40
     * @param \Flugg\Responder\Resources\DataNormalizer                   $normalizer
41
     * @param \Flugg\Responder\Contracts\Transformers\TransformerResolver $transformerResolver
42
     */
43 6
    public function __construct(DataNormalizer $normalizer, TransformerResolver $transformerResolver)
44
    {
45 6
        $this->normalizer = $normalizer;
0 ignored issues
show
Documentation Bug introduced by
It seems like $normalizer of type object<Flugg\Responder\Resources\DataNormalizer> is incompatible with the declared type object<Flugg\Responder\DataNormalizer> of property $normalizer.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
46 6
        $this->transformerResolver = $transformerResolver;
47 6
    }
48
49
    /**
50
     * Make resource from the given data.
51
     *
52
     * @param  mixed                                                          $data
53
     * @param  \Flugg\Responder\Transformers\Transformer|string|callable|null $transformer
54
     * @param  string|null                                                    $resourceKey
55
     * @return \League\Fractal\Resource\ResourceInterface
56
     */
57 6
    public function make($data = null, $transformer = null, string $resourceKey = null): ResourceInterface
58
    {
59 6
        if ($data instanceof ResourceInterface) {
60 1
            return $data->setTransformer($this->resolveTransformer($data->getData(), $transformer ?: $data->getTransformer()));
0 ignored issues
show
Bug introduced by
It seems like $this->resolveTransforme...data->getTransformer()) targeting Flugg\Responder\Resource...y::resolveTransformer() can also be of type null; however, League\Fractal\Resource\...rface::setTransformer() does only seem to accept callable, maybe add an additional type check?

This check looks at variables that are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
61 5
        } elseif (is_null($data = $this->normalizer->normalize($data))) {
62 1
            return $this->instatiateResource($data);
63
        }
64
65 4
        $transformer = $this->resolveTransformer($data, $transformer);
66
67 4
        return $this->instatiateResource($data, $transformer, $resourceKey);
68
    }
69
70
    /**
71
     * Resolve a transformer.
72
     *
73
     * @param  mixed                                                          $data
74
     * @param  \Flugg\Responder\Transformers\Transformer|string|callable|null $transformer
75
     * @return \Flugg\Responder\Transformers\Transformer|callable
0 ignored issues
show
Documentation introduced by
Should the return type not be callable|null?

This check compares the return type specified in the @return annotation of a function or method doc comment with the types returned by the function and raises an issue if they mismatch.

Loading history...
76
     */
77 5
    protected function resolveTransformer($data, $transformer)
78
    {
79 5
        if (isset($transformer)) {
80 3
            return $this->transformerResolver->resolve($transformer);
81
        }
82
83 2
        return $this->transformerResolver->resolveFromData($data);
84
    }
85
86
    /**
87
     * Instatiate a new resource instance.
88
     *
89
     * @param  mixed                                                   $data
90
     * @param  \Flugg\Responder\Transformers\Transformer|callable|null $transformer
91
     * @param  string|null                                             $resourceKey
92
     * @return \League\Fractal\Resource\ResourceInterface
93
     */
94 5
    protected function instatiateResource($data, $transformer = null, string $resourceKey = null): ResourceInterface
95
    {
96 5
        if (is_null($data)) {
97 1
            return new NullResource;
98 4
        } elseif ($this->shouldCreateCollection($data)) {
99 1
            return new CollectionResource($data, $transformer, $resourceKey);
100
        }
101
102 3
        return new ItemResource($data, $transformer, $resourceKey);
103
    }
104
105
    /**
106
     * Indicates if the data belongs to a collection resource.
107
     *
108
     * @param  mixed $data
109
     * @return bool
110
     */
111 4
    protected function shouldCreateCollection($data): bool
112
    {
113 4
        if (is_array($data)) {
114 2
            return ! is_scalar(Arr::first($data));
115
        }
116
117 2
        return $data instanceof Traversable;
118
    }
119
}