GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Push — develop ( fdb351...008b6e )
by Stuart
05:27
created

Output::startPhaseGroup()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 12
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 12
rs 9.4286
cc 2
eloc 5
nc 2
nop 3
1
<?php
2
3
/**
4
 * Copyright (c) 2011-present Mediasift Ltd
5
 * All rights reserved.
6
 *
7
 * Redistribution and use in source and binary forms, with or without
8
 * modification, are permitted provided that the following conditions
9
 * are met:
10
 *
11
 *   * Redistributions of source code must retain the above copyright
12
 *     notice, this list of conditions and the following disclaimer.
13
 *
14
 *   * Redistributions in binary form must reproduce the above copyright
15
 *     notice, this list of conditions and the following disclaimer in
16
 *     the documentation and/or other materials provided with the
17
 *     distribution.
18
 *
19
 *   * Neither the names of the copyright holders nor the names of his
20
 *     contributors may be used to endorse or promote products derived
21
 *     from this software without specific prior written permission.
22
 *
23
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26
 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27
 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
28
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
29
 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
31
 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
33
 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34
 * POSSIBILITY OF SUCH DAMAGE.
35
 *
36
 * @category  Libraries
37
 * @package   Storyplayer/OutputLib
38
 * @author    Stuart Herbert <[email protected]>
39
 * @copyright 2011-present Mediasift Ltd www.datasift.com
40
 * @license   http://www.opensource.org/licenses/bsd-license.php  BSD License
41
 * @link      http://datasift.github.io/storyplayer
42
 */
43
44
namespace DataSift\Storyplayer;
45
46
use Exception;
47
use DataSift\Storyplayer\Phases\Phase;
48
use DataSift\Storyplayer\PlayerLib\Phase_Result;
49
use DataSift\Storyplayer\PlayerLib\PhaseGroup_Result;
50
use DataSift\Storyplayer\PlayerLib\Story_Result;
51
use DataSift\Storyplayer\OutputLib\OutputPlugin;
52
use DataSift\Storyplayer\Console\DefaultConsole;
53
use DataSift\Storyplayer\Console\Console;
54
55
use Phix_Project\ContractLib2\Contract;
56
57
/**
58
 * all output goes through here
59
 *
60
 * @category  Libraries
61
 * @package   Storyplayer/OutputLib
62
 * @author    Stuart Herbert <[email protected]>
63
 * @copyright 2011-present Mediasift Ltd www.datasift.com
64
 * @license   http://www.opensource.org/licenses/bsd-license.php  BSD License
65
 * @link      http://datasift.github.io/storyplayer
66
 */
67
class Output extends OutputPlugin
68
{
69
    /**
70
     * a list of the plugins that are currently active
71
     *
72
     * @var array
73
     */
74
    protected $plugins = [];
75
76
    /**
77
     * a list of the log messages that we have been asked to output
78
     *
79
     * this is used for producing detailed error reports when something
80
     * has gone badly wrong
81
     *
82
     * @var array
83
     */
84
    protected $activityLog = [];
85
86
    /**
87
     * constructor
88
     *
89
     * ensures we have a default console that is connected to stdout
90
     */
91
    public function __construct()
92
    {
93
        // we need a default output for the console
94
        $console = new DefaultConsole();
95
        $console->addOutputToStdout();
96
97
        $this->usePluginAsConsole($console);
98
    }
99
100
    /**
101
     * make a plugin the one that we use when writing to the user's
102
     * console
103
     *
104
     * @param  Console $plugin
105
     *         the plugin that we want
106
     *
107
     * @return void
108
     */
109
    public function usePluginAsConsole(Console $plugin)
110
    {
111
        $this->plugins['console'] = $plugin;
112
    }
113
114
    /**
115
     * set the plugin for a named output slot
116
     *
117
     * @param OutputPlugin $plugin
118
     *        the plugin to use in the slot
119
     * @param string       $slotName
120
     *        the name of the slot to use for this plugin
121
     */
122
    public function usePluginInSlot(OutputPlugin $plugin, $slotName)
123
    {
124
        // enforce our inputs
125
        Contract::RequiresValue($slotName, is_string($slotName));
126
127
        // put the plugin in the required slot
128
        $this->plugins[$slotName] = $plugin;
129
    }
130
131
    /**
132
     * get the array of all plugins
133
     *
134
     * @return array
135
     */
136
    public function getPlugins()
137
    {
138
        return $this->plugins;
139
    }
140
141
    /**
142
     * return the active plugin in the 'console' slot
143
     *
144
     * @return Console|null
145
     */
146
    public function getActiveConsolePlugin()
147
    {
148
        // we ALWAYS have a console plugin :)
149
        return $this->plugins['console'];
150
    }
151
152
    /**
153
     * return the active plugin in the named slot
154
     *
155
     * @param  string $slotName
156
     * @return OutputPlugin|null
157
     */
158
    public function getActivePluginInSlot($slotName)
159
    {
160
        // enforce our inputs
161
        Contract::RequiresValue($slotName, is_string($slotName));
162
163
        // do we have a plugin in this slot?
164
        if (isset($this->plugins[$slotName])) {
165
            return $this->plugins[$slotName];
166
        }
167
168
        // no, we do not
169
        return null;
170
    }
171
172
    /**
173
     * disable 'silent' mode
174
     *
175
     * NOTE: it is up to each plugin in turn whether or not to support
176
     * 'silent' mode at all
177
     *
178
     * @return void
179
     */
180
    public function resetSilentMode()
181
    {
182
        foreach ($this->plugins as $plugin)
183
        {
184
            $plugin->resetSilentMode();
185
        }
186
    }
187
188
    /**
189
     * switches 'silent' mode on
190
     *
191
     * in 'silent' mode, we do not write log activity to the output writer
192
     * at all.  HOWEVER, the plugin may still add the log activity to any
193
     * internal cache it has (can be useful for error reports etc)
194
     *
195
     * @return void
196
     */
197
    public function setSilentMode()
198
    {
199
        foreach ($this->plugins as $plugin)
200
        {
201
            $plugin->setSilentMode();
202
        }
203
    }
204
205
    /**
206
     * switches 'verbose' mode on or off
207
     *
208
     * in 'non-verbose' mode, each output plugin is free to supress some of
209
     * the output, for the sake of asthetics
210
     *
211
     * @param boolean $isVerbose
212
     *        do we want verbose mode or not?
213
     */
214
    public function setIsVerbose($isVerbose)
215
    {
216
        foreach ($this->plugins as $plugin)
217
        {
218
            $plugin->setIsVerbose($isVerbose);
219
        }
220
    }
221
222
    /**
223
     * disables any colour output
224
     *
225
     * @return void
226
     */
227
    public function disableColourSupport()
228
    {
229
        foreach ($this->plugins as $plugin)
230
        {
231
            $plugin->disableColourSupport();
232
        }
233
    }
234
235
    /**
236
     * forces switching on colour support
237
     *
238
     * @return void
239
     */
240
    public function enforceColourSupport()
241
    {
242
        foreach ($this->plugins as $plugin)
243
        {
244
            $plugin->enforceColourSupport();
245
        }
246
    }
247
248
    /**
249
     * asks each active plugin to switch on colour support if possible
250
     *
251
     * a plugin may still choose to not output colour. one example of this
252
     * are consoles. they're happy to output colour if talking to a terminal,
253
     * but choose not to output colour if they're only writing to log files
254
     * or to a pipe into another UNIX process.
255
     *
256
     * @return void
257
     */
258
    public function enableColourSupport()
259
    {
260
        foreach ($this->plugins as $plugin)
261
        {
262
            $plugin->enableColourSupport();
263
        }
264
    }
265
266
    /**
267
     * called when storyplayer starts
268
     *
269
     * @param string $version
270
     * @param string $url
271
     * @param string $copyright
272
     * @param string $license
273
     * @return void
274
     */
275
    public function startStoryplayer($version, $url, $copyright, $license)
276
    {
277
        // enforce our inputs
278
        Contract::RequiresValue($version,   is_string($version));
279
        Contract::RequiresValue($url,       is_string($url));
280
        Contract::RequiresValue($copyright, is_string($copyright));
281
        Contract::RequiresValue($license,   is_string($license));
282
283
        // call all of our plugins
284
        foreach ($this->plugins as $plugin)
285
        {
286
            $plugin->startStoryplayer($version, $url, $copyright, $license);
287
        }
288
    }
289
290
    /**
291
     * called when Storyplayer exits
292
     *
293
     * @param  float $duration
294
     *         how long did storyplayer take to run (in seconds)?
295
     * @return void
296
     */
297
    public function endStoryplayer($duration)
298
    {
299
        foreach ($this->plugins as $plugin)
300
        {
301
            $plugin->endStoryplayer($duration);
302
        }
303
    }
304
305
    /**
306
     * called when we start playing a new PhaseGroup
307
     *
308
     * @param  string $activity
309
     *         what are we doing? (e.g. 'creating', 'running')
310
     * @param  string $name
311
     *         the name of the phase group
312
     * @param  array|null $details
313
     *         optional explanation of what this PhaseGroup is trying
314
     *         to achieve
315
     * @return void
316
     */
317
    public function startPhaseGroup($activity, $name, $details = null)
318
    {
319
        // ensure our inputs!
320
        Contract::RequiresValue($activity, is_string($activity));
321
        Contract::RequiresValue($name,     is_string($name));
322
323
        // call our plugins
324
        foreach ($this->plugins as $plugin)
325
        {
326
            $plugin->startPhaseGroup($activity, $name, $details);
327
        }
328
    }
329
330
    /**
331
     * called when we have finished playing a PhaseGroup
332
     *
333
     * NOTE: we cannot use a type-hint for $result here. we may pass in
334
     * a class that inherits from PhaseGroup_Result, and (annoyingly)
335
     * this isn't allowed if we use a type-hint (grrrr)
336
     *
337
     * @param  PhaseGroup_Result $result
338
     * @return void
339
     */
340
    public function endPhaseGroup($result)
341
    {
342
        // enforce our input type
343
        Contract::Requires($result instanceof PhaseGroup_Result);
344
345
        // call our plugins
346
        foreach ($this->plugins as $plugin)
347
        {
348
            $plugin->endPhaseGroup($result);
349
        }
350
    }
351
352
    /**
353
     * called when a story starts a new phase
354
     *
355
     * $param  Phase $phase
356
     *         the phase that we are executing
357
     * @return void
358
     */
359
    public function startPhase($phase)
360
    {
361
        // enforce our input type
362
        Contract::Requires($phase instanceof Phase);
363
364
        foreach ($this->plugins as $plugin)
365
        {
366
            $plugin->startPhase($phase);
367
        }
368
    }
369
370
    /**
371
     * called when a story ends a phase
372
     *
373
     * @param  Phase $phase
374
     *         the phase that has finished
375
     * @param  Phase_Result $phaseResult
376
     *         the result of running $phase
377
     * @return void
378
     */
379
    public function endPhase($phase, $phaseResult)
380
    {
381
        // enforce our input type
382
        Contract::Requires($phase instanceof Phase);
383
        Contract::Requires($phaseResult instanceof Phase_Result);
384
385
        // inject the captured activity into the phase
386
        $phaseResult->activityLog = $this->activityLog;
387
        $this->activityLog=[];
388
389
        // pass the phase on
390
        foreach ($this->plugins as $plugin)
391
        {
392
            $plugin->endPhase($phase, $phaseResult);
393
        }
394
    }
395
396
    /**
397
     * called when a story logs an action
398
     *
399
     * @param string $msg
400
     *        the message to write to the logs / console
401
     * @param array|null $codeLine
402
     *        information about the line of code that is executing
403
     * @return void
404
     */
405 View Code Duplication
    public function logPhaseActivity($msg, $codeLine = null)
406
    {
407
        // enforce our input type
408
        Contract::RequiresValue($msg, is_string($msg));
409
        if ($codeLine) {
410
            Contract::RequiresValue($codeLine, is_array($codeLine));
411
        }
412
413
        // keep track of what was attempted, in case we need to show
414
        // the user what was attempted
415
        $this->activityLog[] = [
416
            'ts'       => time(),
417
            'text'     => $msg,
418
            'codeLine' => $codeLine,
419
            'isOutput' => false,
420
        ];
421
422
        // call all of our plugins
423
        foreach ($this->plugins as $plugin)
424
        {
425
            $plugin->logPhaseActivity($msg, $codeLine);
426
        }
427
    }
428
429
    /**
430
     * called when a story logs the (possibly partial) output from
431
     * running a subprocess
432
     *
433
     * @param  string $msg the output to log
434
     * @return void
435
     */
436
    public function logPhaseSubprocessOutput($msg)
437
    {
438
        // enforce our input type
439
        Contract::RequiresValue($msg, is_string($msg));
440
441
        // keep track of what was attempted, in case we need to show
442
        // the user what was attempted
443
        $this->activityLog[] = [
444
            'ts'       => time(),
445
            'text'     => $msg,
446
            'codeLine' => null,
447
            'isOutput' => true,
448
        ];
449
450
        // call all of our plugins
451
        foreach ($this->plugins as $plugin)
452
        {
453
            $plugin->logPhaseSubprocessOutput($msg);
454
        }
455
    }
456
457
    /**
458
     * called when a story logs an error
459
     *
460
     * @param string $phaseName
461
     *        the name of the phase where the error occurred
462
     * @param string $msg
463
     *        an error message to send to console|logfile
464
     * @return void
465
     */
466 View Code Duplication
    public function logPhaseError($phaseName, $msg)
467
    {
468
        // enforce our inputs
469
        Contract::RequiresValue($phaseName, is_string($phaseName));
470
        Contract::RequiresValue($msg,       is_string($msg));
471
472
        // keep track of what was attempted, in case we need to show
473
        // the user what was attempted
474
        $this->activityLog[] = [
475
            'ts'       => time(),
476
            'text'     => $msg,
477
            'codeLine' => null,
478
        ];
479
480
        // call all of our plugins
481
        foreach ($this->plugins as $plugin)
482
        {
483
            $plugin->logPhaseError($phaseName, $msg);
484
        }
485
    }
486
487
    /**
488
     * called when a story is skipped
489
     *
490
     * @param string $phaseName
491
     *        the name of the phase where the error occurred
492
     * @param string $msg
493
     *        an informational message to send to console|logfile
494
     * @return void
495
     */
496 View Code Duplication
    public function logPhaseSkipped($phaseName, $msg)
497
    {
498
        // enforce our inputs
499
        Contract::RequiresValue($phaseName, is_string($phaseName));
500
        Contract::RequiresValue($msg,       is_string($msg));
501
502
        // keep track of what was attempted, in case we need to show
503
        // the user what was attempted
504
        $this->activityLog[] = [
505
            'ts'       => time(),
506
            'text'     => $msg,
507
            'codeLine' => null,
508
        ];
509
510
        // call all of our plugins
511
        foreach ($this->plugins as $plugin)
512
        {
513
            $plugin->logPhaseSkipped($phaseName, $msg);
514
        }
515
    }
516
517
    /**
518
     * called when we want to record which line of code in a phase is
519
     * currently executing
520
     *
521
     * @param  array $codeLine
522
     *         details about the line of code that is executing
523
     * @return void
524
     */
525
    public function logPhaseCodeLine($codeLine)
526
    {
527
        // enforce our inputs
528
        Contract::RequiresValue($codeLine, is_array($codeLine));
529
530
        // pass it on to all of our plugins
531
        foreach ($this->plugins as $plugin)
532
        {
533
            $plugin->logPhaseCodeLine($codeLine);
534
        }
535
    }
536
537
    /**
538
     * called when the outer CLI shell encounters a fatal error
539
     *
540
     * @param  string $msg
541
     *         the error message to show the user
542
     *
543
     * @return void
544
     */
545
    public function logCliError($msg)
546
    {
547
        // enforce our inputs
548
        Contract::RequiresValue($msg, is_string($msg));
549
550
        // pass it on to our plugins
551
        foreach ($this->plugins as $plugin)
552
        {
553
            $plugin->logCliError($msg);
554
        }
555
    }
556
557
    /**
558
     * called when the outer CLI shell encounters a fatal error
559
     *
560
     * @param  string $msg
561
     *         the error message to show the user
562
     * @param  \Exception $e
563
     *         the exception that caused the error
564
     * @return void
565
     */
566
    public function logCliErrorWithException($msg, $e)
567
    {
568
        // enforce our inputs
569
        Contract::RequiresValue($msg, is_string($msg));
570
        Contract::RequiresValue($e, $e instanceof Exception);
571
572
        // pass this on to our plugins
573
        foreach ($this->plugins as $plugin)
574
        {
575
            $plugin->logCliErrorWithException($msg, $e);
576
        }
577
    }
578
579
    /**
580
     * called when the outer CLI shell needs to publish a warning
581
     *
582
     * @param  string $msg
583
     *         the warning message to show the user
584
     *
585
     * @return void
586
     */
587
    public function logCliWarning($msg)
588
    {
589
        // enforce our inputs
590
        Contract::RequiresValue($msg, is_string($msg));
591
592
        // pass this on to our plugins
593
        foreach ($this->plugins as $plugin)
594
        {
595
            $plugin->logCliWarning($msg);
596
        }
597
    }
598
599
    /**
600
     * called when the outer CLI shell needs to tell the user something
601
     *
602
     * @param  string $msg
603
     *         the message to show the user
604
     *
605
     * @return void
606
     */
607
    public function logCliInfo($msg)
608
    {
609
        // enforce our inputs
610
        Contract::RequiresValue($msg, is_string($msg));
611
612
        // pass this on to our plugins
613
        foreach ($this->plugins as $plugin)
614
        {
615
            $plugin->logCliInfo($msg);
616
        }
617
    }
618
619
    /**
620
     * an alternative to using PHP's built-in var_dump()
621
     *
622
     * @param  string $name
623
     *         a human-readable name to describe $var
624
     *
625
     * @param  mixed $var
626
     *         the variable to dump
627
     *
628
     * @return void
629
     */
630
    public function logVardump($name, $var)
631
    {
632
        // enforce our inputs
633
        Contract::RequiresValue($name, is_string($name));
634
        // $var can be anything, so there is no contract to enforce
635
636
        // pass this on to our plugins
637
        foreach ($this->plugins as $plugin)
638
        {
639
            $plugin->logVardump($name, $var);
640
        }
641
    }
642
}
643