Passed
Pull Request — master (#15)
by mon
02:14
created

UpdateCommand::execute()   C

Complexity

Conditions 10
Paths 170

Size

Total Lines 67

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 67
rs 6.3865
c 0
b 0
f 0
cc 10
nc 170
nop 2

How to fix   Long Method    Complexity   

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
3
namespace FileEye\MimeMap\Command;
4
5
use SebastianBergmann\Comparator\ComparisonFailure;
6
use SebastianBergmann\Comparator\Factory;
7
use SebastianBergmann\Diff\Differ;
8
use SebastianBergmann\Diff\Output\UnifiedDiffOutputBuilder;
9
use Symfony\Component\Console\Command\Command;
10
use Symfony\Component\Console\Input\InputOption;
11
use Symfony\Component\Console\Input\InputInterface;
12
use Symfony\Component\Console\Output\OutputInterface;
13
use Symfony\Component\Yaml\Yaml;
14
use FileEye\MimeMap\Map\AbstractMap;
15
use FileEye\MimeMap\MapHandler;
16
use FileEye\MimeMap\MapUpdater;
17
18
/**
19
 * A Symfony application command to update the MIME type to extension map.
20
 */
21
class UpdateCommand extends Command
22
{
23
    /**
24
     * {@inheritdoc}
25
     */
26
    protected function configure()
27
    {
28
        $this
29
            ->setName('update')
30
            ->setDescription('Updates the MIME-type-to-extension map. Executes the commands in the script file specified by --script, then writes the map to the PHP file where the PHP --class is defined.')
31
            ->addOption(
32
                'script',
33
                null,
34
                InputOption::VALUE_REQUIRED,
35
                'File name of the script containing the sequence of commands to execute to build the default map.',
36
                MapUpdater::getDefaultMapBuildFile()
37
            )
38
            ->addOption(
39
                'class',
40
                null,
41
                InputOption::VALUE_REQUIRED,
42
                'The fully qualified class name of the PHP class storing the map.',
43
                MapHandler::DEFAULT_MAP_CLASS
44
            )
45
            ->addOption(
46
                'diff',
47
                null,
48
                InputOption::VALUE_NONE,
49
                'Report updates.'
50
            )
51
        ;
52
    }
53
54
    /**
55
     * {@inheritdoc}
56
     */
57
    protected function execute(InputInterface $input, OutputInterface $output)
58
    {
59
        $new_map = MapHandler::map('\FileEye\MimeMap\Map\EmptyMap');
60
        $updater = new MapUpdater($new_map);
61
62
        // Executes on an emtpy map the script commands.
63
        $commands = Yaml::parse(file_get_contents($input->getOption('script')));
64
        foreach ($commands as $command) {
65
            $output->writeln("<info>{$command[0]} ...</info>");
66
            try {
67
                $errors = call_user_func_array([$updater, $command[1]], $command[2]);
68
                if (!empty($errors)) {
69
                    foreach ($errors as $error) {
70
                        $output->writeln("<comment>$error.</comment>");
71
                    }
72
                }
73
            } catch (\Exception $e) {
74
                $output->writeln('<error>' . $e->getMessage() . '</error>');
75
                exit(2);
76
            }
77
        }
78
79
        MapHandler::setDefaultMapClass($input->getOption('class'));
80
        $current_map = MapHandler::map();
81
82
        // Check if anything got changed.
83
        $write = true;
84
        if ($input->getOption('diff')) {
85
            $write = false;
0 ignored issues
show
Unused Code introduced by
$write is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
86
            try {
87
                $output->writeln("<info>Checking changes to MIME types ...</info>");
88
                $this->compareMaps($current_map, $new_map, 't');
89
            } catch (\RuntimeException $e) {
90
                $output->writeln('<comment>Changes to MIME types mapping:</comment>');
91
                $output->writeln($e->getMessage());
92
                $write = true;
0 ignored issues
show
Unused Code introduced by
$write is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
93
            }
94
            $write = false;
95
            try {
96
                $output->writeln("<info>Checking changes to MIME type aliases ...</info>");
97
                $this->compareMaps($current_map, $new_map, 'a');
98
            } catch (\RuntimeException $e) {
99
                $output->writeln('<comment>Changes to MIME types aliases:</comment>');
100
                $output->writeln($e->getMessage());
101
                $write = true;
102
            }
103
            try {
104
                $output->writeln("<info>Checking changes to extensions ...</info>");
105
                $this->compareMaps($current_map, $new_map, 'e');
106
            } catch (\RuntimeException $e) {
107
                $output->writeln('<comment>Changes to extensions mapping</comment>');
108
                $output->writeln($e->getMessage());
109
                $write = true;
110
            }
111
        }
112
113
        // If changed, save the new map to the PHP file.
114
        if ($write) {
115
            $updater->writeMapToPhpClassFile($current_map->getFileName());
116
            $output->writeln('<comment>Code updated.</comment>');
117
        } else {
118
            $output->writeln('<info>No changes to mapping.</info>');
119
        }
120
121
        // Reset the new map's map array.
122
        $new_map->reset();
123
    }
124
125
    /**
126
     * Compares two type-to-extension maps by section.
127
     *
128
     * @param AbstractMap $old_map
129
     *   The first map to compare.
130
     * @param AbstractMap $new_map
131
     *   The second map to compare.
132
     * @param string $section
133
     *   The first-level array key to compare: 't' or 'e' or 'a'.
134
     *
135
     * @throws \RuntimeException with diff details if the maps differ.
136
     *
137
     * @return bool
138
     *   True if the maps are equal.
139
     */
140
    protected function compareMaps(AbstractMap $old_map, AbstractMap $new_map, $section)
141
    {
142
        $old_map->sort();
143
        $new_map->sort();
144
        $old = $old_map->getMapArray();
145
        $new = $new_map->getMapArray();
146
147
        $factory = new Factory;
148
        $comparator = $factory->getComparatorFor($old[$section], $new[$section]);
149
        try {
150
            $comparator->assertEquals($old[$section], $new[$section]);
151
            return true;
152
        } catch (ComparisonFailure $failure) {
153
            $old_string = var_export($old[$section], true);
154
            $new_string = var_export($new[$section], true);
155
            if (class_exists('\SebastianBergmann\Diff\Output\UnifiedDiffOutputBuilder')) {
156
                $differ = new Differ(new UnifiedDiffOutputBuilder("--- Removed\n+++ Added\n"));
157
                throw new \RuntimeException($differ->diff($old_string, $new_string));
158
            } else {
159
                throw new \RuntimeException(' ');
160
            }
161
        }
162
    }
163
}
164