Completed
Push — master ( 5ad1da...0209da )
by Julien
04:14
created

InstallerCommand::configure()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 54
Code Lines 42

Duplication

Lines 0
Ratio 0 %

Importance

Changes 2
Bugs 0 Features 0
Metric Value
c 2
b 0
f 0
dl 0
loc 54
rs 9.6716
cc 2
eloc 42
nc 2
nop 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
3
/**
4
 * Pickle
5
 *
6
 *
7
 * @license
8
 *
9
 * New BSD License
10
 *
11
 * Copyright © 2015-2015, Pickle community. All rights reserved.
12
 *
13
 * Redistribution and use in source and binary forms, with or without
14
 * modification, are permitted provided that the following conditions are met:
15
 *     * Redistributions of source code must retain the above copyright
16
 *       notice, this list of conditions and the following disclaimer.
17
 *     * Redistributions in binary form must reproduce the above copyright
18
 *       notice, this list of conditions and the following disclaimer in the
19
 *       documentation and/or other materials provided with the distribution.
20
 *     * Neither the name of the Hoa nor the names of its contributors may be
21
 *       used to endorse or promote products derived from this software without
22
 *       specific prior written permission.
23
 *
24
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
25
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS AND CONTRIBUTORS BE
28
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
29
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
30
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
31
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
32
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
33
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34
 * POSSIBILITY OF SUCH DAMAGE.
35
 */
36
37
namespace Pickle\Console\Command;
38
39
use Symfony\Component\Console\Command\Command;
40
use Symfony\Component\Console\Input\InputArgument;
41
use Symfony\Component\Console\Input\InputInterface;
42
use Symfony\Component\Console\Input\InputOption;
43
use Symfony\Component\Console\Output\OutputInterface;
44
use Symfony\Component\Console\Question\ConfirmationQuestion;
45
use Symfony\Component\Console\Question\ChoiceQuestion;
46
use Symfony\Component\Console\Question\Question;
47
use Symfony\Component\Console\Helper\Table;
48
use Pickle\Base\Interfaces\Package;
49
use Pickle\Base\Abstracts\Console\Command\BuildCommand;
50
use Pickle\Engine;
51
use Pickle\Package\Util\Windows;
52
use Pickle\Package\Command\Install;
53
use Pickle\Base\Util;
54
55
class InstallerCommand extends BuildCommand
56
{
57
    protected function configure()
58
    {
59
        parent::configure();
60
61
        $this
62
            ->setName('install')
63
            ->setDescription('Install a php extension')
64
            ->addOption(
65
                'dry-run',
66
                null,
67
                InputOption::VALUE_NONE,
68
                'Do not install extension'
69
            )
70
            ->addOption(
71
                'php',
72
                null,
73
                InputOption::VALUE_REQUIRED,
74
                'path to an alternative php (exec)'
75
            )
76
            ->addOption(
77
                'ini',
78
                null,
79
                InputOption::VALUE_REQUIRED,
80
                'path to an alternative php.ini'
81
            )
82
            ->addOption(
83
                'source',
84
                null,
85
                InputOption::VALUE_NONE,
86
                'use source package'
87
            )
88
            ->addOption(
89
                'save-logs',
90
                null,
91
                InputOption::VALUE_REQUIRED,
92
                'path to save the build logs'
93
            )
94
            ->addOption(
95
                'tmp-dir',
96
                null,
97
                InputOption::VALUE_REQUIRED,
98
                'path to a custom temp dir',
99
                sys_get_temp_dir()
100
            );
101
102
        if (defined('PHP_WINDOWS_VERSION_MAJOR')) {
103
            $this->addOption(
104
                'binary',
105
                null,
106
                InputOption::VALUE_NONE,
107
                'use binary package'
108
            );
109
        }
110
    }
111
112
    /**
113
     * @param string          $path
114
     * @param InputInterface  $input
115
     * @param OutputInterface $output
116
     */
117
    protected function binaryInstallWindows($path, InputInterface $input, OutputInterface $output)
118
    {
119
        $php = Engine::factory();
120
        $table = new Table($output);
121
        $table
122
            ->setRows([
123
               ['<info>'.$php->getName().' Path</info>', $php->getPath()],
124
               ['<info>'.$php->getName().' Version</info>', $php->getVersion()],
125
               ['<info>Compiler</info>', $php->getCompiler()],
126
               ['<info>Architecture</info>', $php->getArchitecture()],
127
               ['<info>Thread safety</info>', $php->getZts() ? 'yes' : 'no'],
128
               ['<info>Extension dir</info>', $php->getExtensionDir()],
129
               ['<info>php.ini</info>', $php->getIniPath()],
130
            ])
131
            ->render();
132
133
        $inst = Install::factory($path);
134
        $progress = $this->getHelperSet()->get('progress');
135
        $inst->setProgress($progress);
136
        $inst->setInput($input);
137
        $inst->setOutput($output);
138
        $inst->install();
139
140
        $deps_handler = new Windows\DependencyLib($php);
141
        $deps_handler->setProgress($progress);
142
        $deps_handler->setInput($input);
143
        $deps_handler->setOutput($output);
144
145
        $helper = $this->getHelperSet()->get('question');
146
147
        $cb = function ($choices) use ($helper, $input, $output) {
148
            $question = new ChoiceQuestion(
149
                'Multiple choices found, please select the appropriate dependency package',
150
                $choices
151
            );
152
            $question->setMultiselect(false);
153
154
            return $helper->ask($input, $output, $question);
155
        };
156
157
        foreach ($inst->getExtDllPaths() as $dll) {
158
            if (!$deps_handler->resolveForBin($dll, $cb)) {
159
                throw new \Exception('Failed to resolve dependencies');
160
            }
161
        }
162
    }
163
164
    /*  The most of this needs to be incapsulated into an extra Build class*/
165
    protected function sourceInstall($package, InputInterface $input, OutputInterface $output, $optionsValue = [], $force_opts = '')
166
    {
167
        $helper = $this->getHelperSet()->get('question');
168
169
        $build = \Pickle\Package\Command\Build::factory($package, $optionsValue);
170
171
        try {
172
            $build->prepare();
173
            $build->createTempDir($package->getUniqueNameForFs());
174
            $build->configure($force_opts);
175
            $build->make();
176
            $build->install();
177
178
            $this->saveBuildLogs($input, $build);
179
        } catch (\Exception $e) {
180
            $this->saveBuildLogs($input, $build);
181
182
            $output->writeln('The following error(s) happened: '.$e->getMessage());
183
            $prompt = new ConfirmationQuestion('Would you like to read the log?', true);
184
            if ($helper->ask($input, $output, $prompt)) {
185
                $output->write($build->getLog());
186
            }
187
        }
188
        $build->cleanup();
189
    }
190
191
    protected function execute(InputInterface $input, OutputInterface $output)
192
    {
193
        $path = rtrim($input->getArgument('path'), '/\\');
194
        Util\TmpDir::set($input->getOption('tmp-dir'));
195
196
        /* if windows, try bin install by default */
197
        if (defined('PHP_WINDOWS_VERSION_MAJOR')) {
198
            $sourceRequested = $input->getOption('source');
199
            if (!$sourceRequested) {
200
                $this->binaryInstallWindows($path, $input, $output);
201
202
                return 0;
203
            }
204
        }
205
206
        $package = $this->getHelper('package')->convey($input, $output, $path);
207
208
        /* TODO Info package command should be used here. */
209
        $this->getHelper('package')->showInfo($output, $package);
210
211
        list($optionsValue, $force_opts) = $this->buildOptions($package, $input, $output);
212
213
        if ($input->getOption('dry-run')) {
214
            return 0;
215
        }
216
217
        $this->sourceInstall($package, $input, $output, $optionsValue, $force_opts);
218
219
        return 0;
220
    }
221
}
222
223
/* vim: set tabstop=4 shiftwidth=4 expandtab: fdm=marker */
224