Completed
Push — master ( 759a3c...0a5dc9 )
by Mohamed
04:06
created

CreateCategoryCommand::validateParent()   B

Complexity

Conditions 6
Paths 4

Size

Total Lines 15
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 7
CRAP Score 6

Importance

Changes 3
Bugs 0 Features 0
Metric Value
cc 6
eloc 8
c 3
b 0
f 0
nc 4
nop 1
dl 0
loc 15
ccs 7
cts 7
cp 1
crap 6
rs 8.8571
1
<?php
2
3
/*
4
 * This file is part of the Moo\FlashCardBundle package.
5
 *
6
 * (c) Mohamed Alsharaf <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Moo\FlashCardBundle\Command;
13
14
use Moo\FlashCardBundle\Entity;
15
use Symfony\Component\Console\Input\InputArgument;
16
use Symfony\Component\Console\Input\InputInterface;
17
use Symfony\Component\Console\Input\InputOption;
18
use Symfony\Component\Console\Output\OutputInterface;
19
20
/**
21
 * CreateCardCommand is a command line class for creating a new card category.
22
 *
23
 * @author Mohamed Alsharaf <[email protected]>
24
 */
25
class CreateCategoryCommand extends AbstractCommand
26
{
27
    /**
28
     * An instance of category entity
29
     *
30
     * @var Entity\Category
31
     */
32
    protected $entity;
33
34
    /**
35
     * Get a category entity
36
     *
37
     * @return Entity\Category
38
     */
39 6
    protected function getEntity()
40
    {
41 6
        if (null === $this->entity) {
42 6
            $this->entity = new Entity\Category();
43
        }
44
45 6
        return $this->entity;
46
    }
47
48
    /**
49
     * Command configuration
50
     * Create a new category
51
     *
52
     * @return void
53
     */
54 12
    protected function configure()
55
    {
56
        $this
57 12
            ->setName('flashcard:category:create')
58 12
            ->setDescription('Create a category')
59 12
            ->addArgument('title', InputArgument::REQUIRED, 'The category title.')
60 12
            ->addArgument('desc', InputArgument::OPTIONAL, 'The category description.')
61 12
            ->addArgument('parent', InputArgument::OPTIONAL, 'The parent category ID.')
62 12
            ->addOption('active', null, InputOption::VALUE_NONE, 'If set, the category is going to be active.');
63 12
    }
64
65
    /**
66
     * Enable interaction
67
     *
68
     * @param InputInterface  $input
69
     * @param OutputInterface $output
70
     */
71 3
    protected function interact(InputInterface $input, OutputInterface $output)
72
    {
73 3 View Code Duplication
        if (!$input->getArgument('title')) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
74 3
            $value = $this->getHelper('dialog')->askAndValidate($output, 'Please enter (Title): ',
75 3
                [$this, 'validateTitle'], 1);
76 2
            $input->setArgument('title', $value);
77
        }
78
79 2 View Code Duplication
        if (!$input->getArgument('parent')) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
80 2
            $value = $this->getHelper('dialog')->askAndValidate($output, 'Please enter (Parent category ID): ',
81 2
                [$this, 'validateParent'], 1);
82 1
            $input->setArgument('parent', $value);
83
        }
84 1
    }
85
86
    /**
87
     * Validate the category title
88
     *
89
     * @param string $value
90
     *
91
     * @return string
92
     *
93
     * @throws \Exception
94
     */
95 3
    public function validateTitle($value)
96
    {
97
        // Set title to entity
98 3
        $this->getEntity()->setTitle($value);
99
100
        // Validate entity and return the first error found in property 'title'
101 3
        $errors = $this->getValidator()->validate($this->entity);
102 3
        foreach ($errors as $error) {
103 1
            if ($error->getPropertyPath() == 'title') {
104 1
                throw new \InvalidArgumentException($error->getMessage());
105
            }
106
        }
107
108 2
        return $value;
109
    }
110
111
    /**
112
     * Validate the category parent
113
     *
114
     * @param string $value
115
     *
116
     * @return Entity\Category
117
     *
118
     * @throws \Exception
119
     */
120 2
    public function validateParent($value)
121
    {
122 2
        if ($value < 0 && ($value !== '' || $value !== null)) {
123
            throw new \InvalidArgumentException('The parent category ID must be a positve integer.');
124
        }
125
126 2
        if ($value > 0) {
127 2
            if (!($parent = $this->getRepository('category')->find($value))) {
128 1
                throw new \InvalidArgumentException('The parent category ID is invalid.');
129
            }
130 1
            $this->getEntity()->setParent($parent);
131
        }
132
133 1
        return $value;
134
    }
135
136
    /**
137
     * Execute the command line to create a new category.
138
     *
139
     * @param InputInterface  $input
140
     * @param OutputInterface $output
141
     *
142
     * @return bool
143
     */
144 4
    protected function execute(InputInterface $input, OutputInterface $output)
145
    {
146 4
        $repository = $this->getRepository('category');
147 4
        $category = $this->getEntity();
148 4
        $parent = $input->getArgument('parent');
149
150
        // Setup category entity
151 4
        $category->setCreated();
152 4
        $category->setTitle($input->getArgument('title'));
153 4
        $category->setDescription($input->getArgument('desc'));
154 4
        $category->setActive((boolean) $input->getOption('active'));
0 ignored issues
show
Documentation introduced by
(bool) $input->getOption('active') is of type boolean, but the function expects a integer.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
155 4
        if (!$input->isInteractive() && $parent > 0) {
156 1
            $category->setParent($repository->find($parent));
157
        }
158
159
        // Valid category
160 4
        $errors = $this->getValidator()->validate($category);
161 4
        if (count($errors) > 0) {
162 1
            foreach ($errors as $error) {
163 1
                $this->error($output, $error);
164
            }
165
166 1
            return;
167
        }
168
169
        // Insert category into the database
170 3
        $em = $this->getDoctrine()->getManager();
171 3
        $em->persist($category);
172 3
        $em->flush();
173
174 3
        $this->success($output, 'Voila... You have created a new category.');
175 3
    }
176
}
177