Completed
Push — master ( 4dbd37...a699b3 )
by Sebastian
02:59
created

Runner::__construct()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 4
rs 10
cc 1
eloc 2
nc 1
nop 1
1
<?php
2
namespace phpbu\App;
3
4
use phpbu\App\Backup;
5
use phpbu\App\Backup\Collector;
6
use phpbu\App\Backup\Compressor;
7
use phpbu\App\Backup\Target;
8
9
/**
10
 * Runner actually executes all backup jobs.
11
 *
12
 * @package    phpbu
13
 * @subpackage App
14
 * @author     Sebastian Feldmann <[email protected]>
15
 * @copyright  Sebastian Feldmann <[email protected]>
16
 * @license    https://opensource.org/licenses/MIT The MIT License (MIT)
17
 * @link       http://phpbu.de/
18
 * @since      Class available since Release 1.0.0
19
 */
20
class Runner
21
{
22
    /**
23
     * phpbu Factory
24
     *
25
     * @var \phpbu\App\Factory
26
     */
27
    protected $factory;
28
29
    /**
30
     * Application result
31
     *
32
     * @var \phpbu\App\Result
33
     */
34
    protected $result;
35
36
    /**
37
     * Backup failed
38
     *
39
     * @var boolean
40
     */
41
    protected $failure;
42
43
    /**
44
     * App Configuration
45
     *
46
     * @var \phpbu\App\Configuration
47
     */
48
    protected $configuration;
49
50
    /**
51
     * Constructor
52
     *
53
     * @param \phpbu\App\Factory $factory
54
     */
55
    public function __construct(Factory $factory)
56
    {
57
        $this->factory = $factory;
58
    }
59
60
    /**
61
     * Run phpbu
62
     *
63
     * @param  \phpbu\App\Configuration $configuration
64
     * @param  \phpbu\App\Factory
65
     * @return \phpbu\App\Result
66
     */
67
    public function run(Configuration $configuration)
68
    {
69
        // TODO: don't rely on static/global settings this is ugly
70
        Util\Cli::registerBase('configuration', $configuration->getWorkingDirectory());
71
72
        $stop                = false;
73
        $this->result        = new Result();
74
        $this->configuration = $configuration;
75
76
        $this->setupEnvironment($configuration);
77
        $this->setupLoggers($configuration);
78
        $this->result->phpbuStart($configuration);
79
80
        // create backups
81
        /** @var \phpbu\App\Configuration\Backup $backup */
82
        foreach ($configuration->getBackups() as $backup) {
83
            if ($stop) {
84
                break;
85
            }
86
            // setup target and collector, reset failure state
87
            $target        = $this->createTarget($backup->getTarget());
88
            $collector     = new Collector($target);
89
            $this->failure = false;
90
91
            try {
92
                /*      ___  ___  _______ ____  _____
93
                 *     / _ )/ _ |/ ___/ //_/ / / / _ \
94
                 *    / _  / __ / /__/ ,< / /_/ / ___/
95
                 *   /____/_/ |_\___/_/|_|\____/_/
96
                 */
97
                $this->executeSource($backup, $target);
98
99
                /*     _______ _____________ ______
100
                 *    / ___/ // / __/ ___/ //_/ __/
101
                 *   / /__/ _  / _// /__/ ,< _\ \
102
                 *   \___/_//_/___/\___/_/|_/___/
103
                 */
104
                $this->executeChecks($backup, $target, $collector);
105
106
                /*     __________  _____  ______
107
                 *    / ___/ _ \ \/ / _ \/_  __/
108
                 *   / /__/ , _/\  / ___/ / /
109
                 *   \___/_/|_| /_/_/    /_/
110
                 */
111
                $this->executeCrypt($backup, $target);
112
113
                /*      ______  ___  ___________
114
                 *     / __/\ \/ / |/ / ___/ __/
115
                 *    _\ \   \  /    / /___\ \
116
                 *   /___/   /_/_/|_/\___/___/
117
                 */
118
                $this->executeSyncs($backup, $target);
119
120
                /*     _______   _______   _  ____  _____
121
                 *    / ___/ /  / __/ _ | / |/ / / / / _ \
122
                 *   / /__/ /__/ _// __ |/    / /_/ / ___/
123
                 *   \___/____/___/_/ |_/_/|_/\____/_/
124
                 */
125
                $this->executeCleanup($backup, $target, $collector);
126
127
            } catch (\Exception $e) {
128
                $this->result->debug('exception: ' . $e->getMessage());
129
                $this->result->addError($e);
130
                $this->result->backupFailed($backup);
131
                if ($backup->stopOnFailure()) {
132
                    $stop = true;
133
                }
134
            }
135
        }
136
        $this->result->phpbuEnd();
137
138
        return $this->result;
139
    }
140
141
    /**
142
     * This executes a bootstrap runner to handle ini settings and the bootstrap file inclusion.
143
     *
144
     * @param  \phpbu\App\Configuration $configuration
145
     * @throws \phpbu\App\Exception
146
     */
147
    protected function setupEnvironment(Configuration $configuration)
148
    {
149
        $runner = $this->factory->createRunner('Bootstrap', $this->configuration->isSimulation());
150
        $runner->run($configuration);
151
    }
152
153
    /**
154
     * Create and register all configured loggers.
155
     *
156
     * @param  \phpbu\App\Configuration $configuration
157
     */
158
    protected function setupLoggers(Configuration $configuration)
159
    {
160
        foreach ($configuration->getLoggers() as $log) {
161
            // this is a already fully setup Listener so just add it
162
            if ($log instanceof Listener) {
163
                $logger = $log;
164
            } else {
165
                // this is a configuration blueprint for a logger, so create and add it
166
                /** @var \phpbu\App\Configuration\Logger $log */
167
                /** @var \phpbu\App\Listener $logger */
168
                $logger = $this->factory->createLogger($log->type, $log->options);
169
            }
170
            $this->result->addListener($logger);
171
        }
172
    }
173
174
    /**
175
     * Create a target.
176
     *
177
     * @param  \phpbu\App\Configuration\Backup\Target $conf
178
     * @return \phpbu\App\Backup\Target
179
     * @throws \phpbu\App\Exception
180
     */
181
    protected function createTarget(Configuration\Backup\Target $conf)
182
    {
183
        $target = new Target($conf->dirname, $conf->filename);
184
        $target->setupPath();
185
        // add possible compressor
186
        if (!empty($conf->compression)) {
187
            $compressor = Compressor::create($conf->compression);
188
            $target->setCompressor($compressor);
189
        }
190
        return $target;
191
    }
192
193
    /**
194
     * Execute the backup.
195
     *
196
     * @param  \phpbu\App\Configuration\Backup $conf
197
     * @param  \phpbu\App\Backup\Target        $target
198
     * @throws \Exception
199
     */
200
    protected function executeSource(Configuration\Backup $conf, Target $target)
201
    {
202
        $this->result->backupStart($conf);
203
        /* @var \phpbu\App\Runner\Source $runner */
204
        $source = $this->factory->createSource($conf->getSource()->type, $conf->getSource()->options);
205
        $runner = $this->factory->createRunner('source', $this->configuration->isSimulation());
206
        $runner->run($source, $target, $this->result);
207
        $this->result->backupEnd($conf);
208
    }
209
210
    /**
211
     * Execute checks.
212
     *
213
     * @param  \phpbu\App\Configuration\Backup $backup
214
     * @param  \phpbu\App\Backup\Target        $target
215
     * @param  \phpbu\App\Backup\Collector     $collector
216
     * @throws \Exception
217
     */
218
    protected function executeChecks(Configuration\Backup $backup, Target $target, Collector $collector)
219
    {
220
        /* @var \phpbu\App\Runner\Check $runner */
221
        /* @var \phpbu\App\Configuration\Backup\Check $check */
222
        $runner = $this->factory->createRunner('check', $this->configuration->isSimulation());
223
        foreach ($backup->getChecks() as $config) {
224
            try {
225
                $this->result->checkStart($config);
226
                $check = $this->factory->createCheck($config->type);
227
                if ($runner->run($check, $target, $config->value, $collector, $this->result)) {
228
                    $this->result->checkEnd($config);
229
                } else {
230
                    $this->failure = true;
231
                    $this->result->checkFailed($config);
232
                }
233
            } catch (Exception $e) {
234
                $this->failure = true;
235
                $this->result->addError($e);
236
                $this->result->checkFailed($config);
237
            }
238
        }
239
    }
240
241
    /**
242
     * Execute encryption.
243
     *
244
     * @param \phpbu\App\Configuration\Backup $backup
245
     * @param \phpbu\App\Backup\Target        $target
246
     */
247 View Code Duplication
    protected function executeCrypt(Configuration\Backup $backup, Target $target)
248
    {
249
        if ($backup->hasCrypt()) {
250
            try {
251
                $crypt = $backup->getCrypt();
252
                $this->result->cryptStart($crypt);
253
                if ($this->failure && $crypt->skipOnFailure) {
254
                    $this->result->cryptSkipped($crypt);
255
                } else {
256
                    /* @var \phpbu\App\Runner\Crypter $runner */
257
                    $runner  = $this->factory->createRunner('crypter', $this->configuration->isSimulation());
258
                    $runner->run($this->factory->createCrypter($crypt->type, $crypt->options), $target, $this->result);
259
                }
260
            } catch (Backup\Crypter\Exception $e) {
261
                $this->failure = true;
262
                $this->result->addError($e);
263
                $this->result->cryptFailed($crypt);
264
            }
265
        }
266
    }
267
268
    /**
269
     * Execute all syncs.
270
     *
271
     * @param  \phpbu\App\Configuration\Backup $backup
272
     * @param  \phpbu\App\Backup\Target        $target
273
     * @throws \Exception
274
     */
275 View Code Duplication
    protected function executeSyncs(Configuration\Backup $backup, Target $target)
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...
276
    {
277
        /* @var \phpbu\App\Runner\Crypter $runner */
278
        /* @var \phpbu\App\Configuration\Backup\Sync $sync */
279
        $runner  = $this->factory->createRunner('sync', $this->configuration->isSimulation());
280
        foreach ($backup->getSyncs() as $sync) {
281
            try {
282
                $this->result->syncStart($sync);
283
                if ($this->failure && $sync->skipOnFailure) {
284
                    $this->result->syncSkipped($sync);
285
                } else {
286
                    $runner->run($this->factory->createSync($sync->type, $sync->options), $target, $this->result);
287
                    $this->result->syncEnd($sync);
288
                }
289
            } catch (Backup\Sync\Exception $e) {
290
                $this->failure = true;
291
                $this->result->addError($e);
292
                $this->result->syncFailed($sync);
293
            }
294
        }
295
    }
296
297
    /**
298
     * Execute the cleanup.
299
     *
300
     * @param  \phpbu\App\Configuration\Backup $backup
301
     * @param  \phpbu\App\Backup\Target        $target
302
     * @param  \phpbu\App\Backup\Collector     $collector
303
     * @throws \Exception
304
     */
305
    protected function executeCleanup(Configuration\Backup $backup, Target $target, Collector $collector)
306
    {
307
        /* @var \phpbu\App\Runner\Cleaner $runner */
308
        /* @var \phpbu\App\Configuration\Backup\Cleanup $cleanup */
309
        if ($backup->hasCleanup()) {
310
            try {
311
                $runner  = $this->factory->createRunner('cleaner', $this->configuration->isSimulation());
312
                $cleanup = $backup->getCleanup();
313
                $this->result->cleanupStart($cleanup);
314
                if ($this->failure && $cleanup->skipOnFailure) {
315
                    $this->result->cleanupSkipped($cleanup);
316
                } else {
317
                    $cleaner = $this->factory->createCleaner($cleanup->type, $cleanup->options);
318
                    $runner->run($cleaner, $target, $collector, $this->result);
319
                    $this->result->cleanupEnd($cleanup);
320
                }
321
            } catch (Backup\Cleaner\Exception $e) {
322
                $this->failure = true;
323
                $this->result->addError($e);
324
                $this->result->cleanupFailed($cleanup);
0 ignored issues
show
Bug introduced by
The variable $cleanup does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
325
            }
326
        }
327
    }
328
}
329