Completed
Push — master ( 51e9c2...0afc07 )
by Oleg
06:21
created

UpdateUserAction::process()   B

Complexity

Conditions 8
Paths 19

Size

Total Lines 53
Code Lines 42

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 33
CRAP Score 8.2327

Importance

Changes 0
Metric Value
cc 8
eloc 42
nc 19
nop 2
dl 0
loc 53
ccs 33
cts 39
cp 0.8462
crap 8.2327
rs 7.1199
c 0
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
declare(strict_types=1);
3
4
namespace SlayerBirden\DataFlowServer\Domain\Controller;
5
6
use Doctrine\DBAL\Exception\UniqueConstraintViolationException;
7
use Doctrine\ORM\EntityManagerInterface;
8
use Doctrine\ORM\ORMException;
9
use Doctrine\ORM\ORMInvalidArgumentException;
10
use Psr\Http\Server\MiddlewareInterface;
11
use SlayerBirden\DataFlowServer\Doctrine\Exception\NonExistingEntity;
12
use SlayerBirden\DataFlowServer\Domain\Entities\User;
13
use SlayerBirden\DataFlowServer\Notification\DangerMessage;
14
use SlayerBirden\DataFlowServer\Notification\SuccessMessage;
15
use Psr\Http\Server\RequestHandlerInterface;
16
use Psr\Http\Message\ResponseInterface;
17
use Psr\Http\Message\ServerRequestInterface;
18
use Psr\Log\LoggerInterface;
19
use Zend\Diactoros\Response\JsonResponse;
20
use Zend\Hydrator\ExtractionInterface;
21
use Zend\Hydrator\HydratorInterface;
22
use Zend\InputFilter\InputFilterInterface;
23
24
class UpdateUserAction implements MiddlewareInterface
25
{
26
    /**
27
     * @var EntityManagerInterface
28
     */
29
    private $entityManager;
30
    /**
31
     * @var HydratorInterface
32
     */
33
    private $hydrator;
34
    /**
35
     * @var InputFilterInterface
36
     */
37
    private $inputFilter;
38
    /**
39
     * @var LoggerInterface
40
     */
41
    private $logger;
42
    /**
43
     * @var ExtractionInterface
44
     */
45
    private $extraction;
46
47 5
    public function __construct(
48
        EntityManagerInterface $entityManager,
49
        HydratorInterface $hydrator,
50
        InputFilterInterface $inputFilter,
51
        LoggerInterface $logger,
52
        ExtractionInterface $extraction
53
    ) {
54 5
        $this->entityManager = $entityManager;
55 5
        $this->hydrator = $hydrator;
56 5
        $this->inputFilter = $inputFilter;
57 5
        $this->logger = $logger;
58 5
        $this->extraction = $extraction;
59 5
    }
60
61
    /**
62
     * @inheritdoc
63
     */
64 5
    public function process(ServerRequestInterface $request, RequestHandlerInterface $handler): ResponseInterface
65
    {
66 5
        $data = $request->getParsedBody();
67 5
        $id = (int)$request->getAttribute('id');
68
69 5
        $this->inputFilter->setData($data);
0 ignored issues
show
Bug introduced by
It seems like $data defined by $request->getParsedBody() on line 66 can also be of type null or object; however, Zend\InputFilter\InputFilterInterface::setData() does only seem to accept array|object<Traversable>, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
70
71 5
        $message = null;
72 5
        $validation = [];
73 5
        $updated = false;
74 5
        $status = 200;
75
76 5
        if ($this->inputFilter->isValid()) {
77
            try {
78 4
                $user = $this->getUser($id, $data);
0 ignored issues
show
Bug introduced by
It seems like $data defined by $request->getParsedBody() on line 66 can also be of type null or object; however, SlayerBirden\DataFlowSer...teUserAction::getUser() does only seem to accept array, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
79 3
                $this->entityManager->persist($user);
80 3
                $this->entityManager->flush();
81 2
                $message = new SuccessMessage('User has been updated!');
82 2
                $updated = true;
83 2
            } catch (NonExistingEntity $exception) {
84 1
                $message = new DangerMessage($exception->getMessage());
85 1
                $status = 404;
86 1
            } catch (ORMInvalidArgumentException $exception) {
87
                $message = new DangerMessage($exception->getMessage());
88
                $status = 400;
89 1
            } catch (UniqueConstraintViolationException $exception) {
90 1
                $message = new DangerMessage('Email address already taken.');
91 1
                $status = 400;
92
            } catch (ORMException $exception) {
93
                $this->logger->error((string)$exception);
94
                $message = new DangerMessage('Error saving user.');
95
                $status = 400;
96
            }
97
        } else {
98 1
            foreach ($this->inputFilter->getInvalidInput() as $key => $input) {
99 1
                $messages = $input->getMessages();
100 1
                $validation[] = [
101 1
                    'field' => $key,
102 1
                    'msg' => reset($messages)
103
                ];
104
            }
105 1
            $status = 400;
106
        }
107
108 5
        return new JsonResponse([
109 5
            'msg' => $message,
110 5
            'success' => $updated,
111
            'data' => [
112 5
                'validation' => $validation,
113 3
                'user' => isset($user) ? $this->extraction->extract($user) : null,
114
            ]
115 5
        ], $status);
116
    }
117
118 4
    private function getUser(int $id, array $data): User
119
    {
120
        /** @var User $user */
121 4
        $user = $this->entityManager->find(User::class, $id);
122 4
        if (!$user) {
123 1
            throw new NonExistingEntity(sprintf('Could not find user by id %d.', $id));
124
        }
125 3
        if (isset($data['id'])) {
126 1
            unset($data['id']);
127
        }
128 3
        $this->hydrator->hydrate($data, $user);
129
130 3
        return $user;
131
    }
132
}
133