Completed
Push — sf/composer-install-update ( a1e834 )
by Kiyotaka
10:44
created

ComposerApiService::execUpdate()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 10

Duplication

Lines 10
Ratio 100 %

Importance

Changes 0
Metric Value
cc 1
nc 1
nop 2
dl 10
loc 10
rs 9.9332
c 0
b 0
f 0
1
<?php
2
3
/*
4
 * This file is part of EC-CUBE
5
 *
6
 * Copyright(c) LOCKON CO.,LTD. All Rights Reserved.
7
 *
8
 * http://www.lockon.co.jp/
9
 *
10
 * For the full copyright and license information, please view the LICENSE
11
 * file that was distributed with this source code.
12
 */
13
14
namespace Eccube\Service\Composer;
15
16
use Composer\Console\Application;
17
use Eccube\Common\EccubeConfig;
18
use Eccube\Exception\PluginException;
19
use Symfony\Component\Console\Input\ArrayInput;
20
use Symfony\Component\Console\Output\BufferedOutput;
21
use Symfony\Component\Console\Output\OutputInterface;
22
23
/**
24
 * Class ComposerApiService
25
 */
26
class ComposerApiService implements ComposerServiceInterface
27
{
28
    /**
29
     * @var EccubeConfig
30
     */
31
    protected $eccubeConfig;
32
33
    /**
34
     * @var Application
35
     */
36
    private $consoleApplication;
37
38
    private $workingDir;
39
40
    public function __construct(EccubeConfig $eccubeConfig)
41
    {
42
        $this->eccubeConfig = $eccubeConfig;
43
    }
44
45
    /**
46
     * Run get info command
47
     *
48
     * @param string $pluginName format foo/bar or foo/bar:1.0.0 or "foo/bar 1.0.0"
49
     *
50
     * @return array
51
     *
52
     * @throws PluginException
53
     */
54
    public function execInfo($pluginName)
55
    {
56
        $output = $this->runCommand([
57
            'command' => 'info',
58
            'package' => $pluginName,
59
        ]);
60
61
        return OutputParser::parseInfo($output);
62
    }
63
64
    /**
65
     * Run execute command
66
     *
67
     * @param string $packageName format "foo/bar foo/bar:1.0.0"
68
     * @param null|OutputInterface $output
69
     *
70
     * @throws PluginException
71
     */
72
    public function execRequire($packageName, $output = null)
73
    {
74
        $packageName = explode(' ', trim($packageName));
75
        $this->runCommand([
76
            'command' => 'require',
77
            'packages' => $packageName,
78
            '--no-interaction' => true,
79
            '--profile' => true,
80
            '--prefer-dist' => true,
81
            '--ignore-platform-reqs' => true,
82
            '--update-with-dependencies' => true,
83
            '--no-scripts' => true,
84
        ], $output);
85
    }
86
87
    /**
88
     * Run remove command
89
     *
90
     * @param string $packageName format "foo/bar foo/bar:1.0.0"
91
     * @param null|OutputInterface $output
92
     *
93
     * @throws PluginException
94
     */
95
    public function execRemove($packageName, $output = null)
96
    {
97
        $packageName = explode(' ', trim($packageName));
98
        $this->runCommand([
99
            'command' => 'remove',
100
            'packages' => $packageName,
101
            '--ignore-platform-reqs' => true,
102
            '--no-interaction' => true,
103
            '--profile' => true,
104
            '--no-scripts' => true,
105
        ], $output);
106
    }
107
108
    /**
109
     * Run update command
110
     *
111
     * @param boolean $dryRun
112
     * @param null|OutputInterface $output
113
     *
114
     * @throws PluginException
115
     */
116 View Code Duplication
    public function execUpdate($dryRun, $output = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
117
    {
118
        $this->runCommand([
119
            'command' => 'update',
120
            '--no-interaction' => true,
121
            '--profile' => true,
122
            '--no-scripts' => true,
123
            '--dry-run' => !!$dryRun,
124
        ], $output);
125
    }
126
127
    /**
128
     * Run install command
129
     *
130
     * @param boolean $dryRun
131
     * @param null|OutputInterface $output
132
     *
133
     * @throws PluginException
134
     */
135 View Code Duplication
    public function execInstall($dryRun, $output = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in 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...
136
    {
137
        $this->runCommand([
138
            'command' => 'install',
139
            '--no-interaction' => true,
140
            '--profile' => true,
141
            '--no-scripts' => true,
142
            '--dry-run' => !!$dryRun,
143
        ], $output);
144
    }
145
146
    /**
147
     * Get require
148
     *
149
     * @param string $packageName
150
     * @param string $callback
151
     * @param null $typeFilter
152
     *
153
     * @throws PluginException
154
     */
155
    public function foreachRequires($packageName, $callback, $typeFilter = null)
156
    {
157
        $info = $this->execInfo($packageName);
158
        if (isset($info['requires'])) {
159
            foreach ($info['requires'] as $name => $version) {
160
                $package = $this->execInfo($name);
161
                if (is_null($typeFilter) || @$package['type'] === $typeFilter) {
162
                    $callback($package);
163
                }
164
            }
165
        }
166
    }
167
168
    /**
169
     * Run get config information
170
     *
171
     * @param string $key
172
     * @param null $value
173
     *
174
     * @return array|mixed
175
     *
176
     * @throws PluginException
177
     */
178
    public function execConfig($key, $value = null)
179
    {
180
        $commands = [
181
            'command' => 'config',
182
            'setting-key' => $key,
183
            'setting-value' => $value,
184
        ];
185
        if ($value) {
186
            $commands['setting-value'] = $value;
187
        }
188
        $output = $this->runCommand($commands);
189
190
        return OutputParser::parseConfig($output);
191
    }
192
193
    /**
194
     * Get config list
195
     *
196
     * @return array
197
     *
198
     * @throws PluginException
199
     */
200
    public function getConfig()
201
    {
202
        $output = $this->runCommand([
203
            'command' => 'config',
204
            '--list' => true,
205
        ]);
206
207
        return OutputParser::parseList($output);
208
    }
209
210
    /**
211
     * Set work dir
212
     *
213
     * @param string $workingDir
214
     */
215
    public function setWorkingDir($workingDir)
216
    {
217
        $this->workingDir = $workingDir;
218
    }
219
220
    /**
221
     * Run composer command
222
     *
223
     * @param array $commands
224
     * @param null|OutputInterface $output
225
     *
226
     * @return string
227
     *
228
     * @throws PluginException
229
     */
230
    public function runCommand($commands, $output = null)
231
    {
232
        $this->init();
233
        $commands['--working-dir'] = $this->workingDir;
234
        $commands['--no-ansi'] = true;
235
        $input = new ArrayInput($commands);
236
        $output = $output ?: new BufferedOutput();
237
238
        $exitCode = $this->consoleApplication->run($input, $output);
239
240
        if ($output instanceof BufferedOutput) {
241
            $log = $output->fetch();
242
            if ($exitCode) {
243
                log_error($log);
244
                throw new PluginException($log);
245
            }
246
            log_info($log, $commands);
247
248
            return $log;
249
        } elseif ($exitCode) {
250
            throw new PluginException();
251
        }
252
    }
253
254
    /**
255
     * Init composer console application
256
     */
257
    private function init()
258
    {
259
        set_time_limit(0);
260
        ini_set('memory_limit', '-1');
261
        // Config for some environment
262
        putenv('COMPOSER_HOME='.$this->eccubeConfig['plugin_realdir'].'/.composer');
263
        $consoleApplication = new Application();
264
        $consoleApplication->resetComposer();
265
        $consoleApplication->setAutoExit(false);
266
        $this->consoleApplication = $consoleApplication;
267
        $this->workingDir = $this->workingDir ? $this->workingDir : $this->eccubeConfig['kernel.project_dir'];
268
    }
269
270
    /**
271
     * Get version of composer
272
     *
273
     * @return null|string
274
     *
275
     * @throws PluginException
276
     */
277
    public function composerVersion()
278
    {
279
        $this->init();
280
        $output = $this->runCommand([
281
            '--version' => true,
282
        ]);
283
284
        return OutputParser::parseComposerVersion($output);
285
    }
286
287
    /**
288
     * Get mode
289
     *
290
     * @return string
291
     */
292
    public function getMode()
293
    {
294
        return 'API';
295
    }
296
}
297