Completed
Pull Request — master (#215)
by Thomas
04:24 queued 30s
created

Application   A

Complexity

Total Complexity 22

Size/Duplication

Total Lines 145
Duplicated Lines 4.14 %

Coupling/Cohesion

Components 1
Dependencies 8

Test Coverage

Coverage 0%

Importance

Changes 3
Bugs 0 Features 0
Metric Value
wmc 22
c 3
b 0
f 0
lcom 1
cbo 8
dl 6
loc 145
ccs 0
cts 95
cp 0
rs 10

8 Methods

Rating   Name   Duplication   Size   Complexity  
A setContainer() 0 4 1
A getContainer() 0 3 1
A getLogger() 0 3 1
A logException() 0 5 1
B doRun() 0 35 5
A doRunCommand() 0 18 3
B assertOwnCloudFound() 6 22 6
A initDirectoryStructure() 0 14 4

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
/**
3
 * @author Victor Dubiniuk <[email protected]>
4
 *
5
 * @copyright Copyright (c) 2015, ownCloud, Inc.
6
 * @license AGPL-3.0
7
 *
8
 * This code is free software: you can redistribute it and/or modify
9
 * it under the terms of the GNU Affero General Public License, version 3,
10
 * as published by the Free Software Foundation.
11
 *
12
 * This program is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
 * GNU Affero General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU Affero General Public License, version 3,
18
 * along with this program.  If not, see <http://www.gnu.org/licenses/>
19
 *
20
 */
21
namespace Owncloud\Updater\Console;
22
23
use Owncloud\Updater\Utils\Locator;
24
use Pimple\Container;
25
use Symfony\Component\Console\Output\StreamOutput;
26
use Symfony\Component\Console\Input\InputInterface;
27
use Symfony\Component\Console\Output\BufferedOutput;
28
use Symfony\Component\Console\Output\OutputInterface;
29
use Symfony\Component\Console\Command\Command;
30
use \Symfony\Component\Process\Exception\ProcessFailedException;
31
32
class Application extends \Symfony\Component\Console\Application {
33
34
	/** @var Container */
35
	public static $container;
36
37
38
	/** @var Container */
39
	protected $diContainer;
40
41
	/**
42
	 * Pass Pimple container into application
43
	 * @param Container $container
44
	 */
45
	public function setContainer(Container $container){
46
		$this->diContainer = $container;
47
		self::$container = $container;
48
	}
49
50
	/**
51
	 * Get Pimple container
52
	 * @return Container
53
	 */
54
	public function getContainer(){
55
		return $this->diContainer;
56
	}
57
58
	/**
59
	 * Get logger instance
60
	 * @return \Psr\Log\LoggerInterface
61
	 */
62
	public function getLogger(){
63
		return $this->diContainer['logger'];
64
	}
65
66
	/**
67
	 * Log exception with trace
68
	 * @param \Exception $e
69
	 */
70
	public function logException($e){
71
			$buffer = new BufferedOutput(OutputInterface::VERBOSITY_VERBOSE);
72
			$this->renderException($e, $buffer);
73
			$this->getLogger()->error($buffer->fetch());
74
	}
75
76
	public function doRun(InputInterface $input, OutputInterface $output){
77
		if (!($this->diContainer['logger.output'] instanceof StreamOutput)){
78
			$output->writeln('[Warning] Failed to init logger. Logging is disabled.');
79
		}
80
		try {
81
			// TODO: check if the current command needs a valid OC instance
82
			$this->assertOwnCloudFound();
83
			$this->initDirectoryStructure();
84
85
			$configReader = $this->diContainer['utils.configReader'];
86
			$commandName = $this->getCommandName($input);
87
			if (!in_array(
88
					$commandName,
89
					['upgrade:executeCoreUpgradeScripts', 'upgrade:checkpoint', 'upgrade:maintenanceMode', 'help', 'list']
90
				)
91
			){
92
				try {
93
					$configReader->init();
94
				} catch (ProcessFailedException $e){
95
					$this->logException($e);
96
					$output->writeln("<error>Initialization failed with message:</error>");
97
					$output->writeln($e->getProcess()->getOutput());
98
					$output->writeln('<info>Use upgrade:checkpoint --list to view a list of checkpoints</info>');
99
					$output->writeln('<info>upgrade:checkpoint --restore [checkpointid] to revert to the last checkpoint</info>');
100
					$output->writeln('Please attach your update.log to the issues you reporting.');
101
					return 1;
102
				}
103
				
104
			}
105
			return parent::doRun($input, $output);
106
		} catch (\Exception $e) {
107
			$this->logException($e);
108
			throw $e;
109
		}
110
	}
111
112
	protected function doRunCommand(Command $command, InputInterface $input, OutputInterface $output){
113
		if ($command instanceof \Owncloud\Updater\Command\Command){
114
			$command->setContainer($this->getContainer());
115
			$commandName = $this->getCommandName($input);
116
			$this->getLogger()->info('Execution of ' . $commandName . ' command started');
117
			if (!empty($command->getMessage())){
118
				$message = sprintf('<info>%s</info>', $command->getMessage());
119
				$output->writeln($message);
120
			}
121
			$exitCode = parent::doRunCommand($command, $input, $output);
122
			$this->getLogger()->info(
123
					'Execution of ' . $commandName . ' command stopped. Exit code is ' . $exitCode
124
			);
125
		} else {
126
			$exitCode = parent::doRunCommand($command, $input, $output);
127
		}
128
		return $exitCode;
129
	}
130
131
	/**
132
	 * Check for owncloud instance
133
	 * @throws \RuntimeException
134
	 */
135
	protected function assertOwnCloudFound(){
136
		$container = $this->getContainer();
137
		/** @var Locator $locator */
138
		$locator = $container['utils.locator'];
139
140
		$file = $locator->getPathToVersionFile();
141 View Code Duplication
		if (!file_exists($file) || !is_file($file)){
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...
142
			throw new \RuntimeException('ownCloud is not found in ' . dirname($file));
143
		}
144
145
		// assert minimum version
146
		$installedVersion = implode('.', $locator->getInstalledVersion());
147
		if (version_compare($installedVersion, '9.0.0', '<')) {
148
			throw new \RuntimeException("Minimum ownCloud version 9.0.0 is required for the updater - $installedVersion was found in " . $locator->getOwncloudRootPath());
149
		}
150
151
		// has to be installed
152
		$file = $locator->getPathtoConfigFile();
153 View Code Duplication
		if (!file_exists($file) || !is_file($file)){
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...
154
			throw new \RuntimeException('ownCloud in ' . dirname($file) . ' is not installed.');
155
		}
156
	}
157
158
	/**
159
	 * Create proper directory structure to store data
160
	 */
161
	protected function initDirectoryStructure(){
162
		$container = $this->getContainer();
163
		$locator = $container['utils.locator'];
164
		$fsHelper = $container['utils.filesystemhelper'];
165
		if (!file_exists($locator->getDataDir())){
166
			$fsHelper->mkdir($locator->getDataDir());
167
		}
168
		if (!file_exists($locator->getDownloadBaseDir())){
169
			$fsHelper->mkdir($locator->getDownloadBaseDir());
170
		}
171
		if (!file_exists($locator->getCheckpointDir())){
172
			$fsHelper->mkdir($locator->getCheckpointDir());
173
		}
174
	}
175
176
}
177