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.
Passed
Pull Request — master (#1061)
by Maxim
04:23 queued 01:35
created

functions.php ➔ ask()   B

Complexity

Conditions 6
Paths 6

Size

Total Lines 22
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 42

Importance

Changes 0
Metric Value
cc 6
eloc 11
nc 6
nop 3
dl 0
loc 22
ccs 0
cts 0
cp 0
crap 42
rs 8.6737
c 0
b 0
f 0
1
<?php
2
/* (c) Anton Medvedev <[email protected]>
3
 *
4
 * For the full copyright and license information, please view the LICENSE
5
 * file that was distributed with this source code.
6
 */
7
namespace Deployer;
8
9
use Deployer\Builder\BuilderInterface;
10
use Deployer\Server\Local;
11
use Deployer\Server\Remote;
12
use Deployer\Server\Builder;
13
use Deployer\Server\Configuration;
14
use Deployer\Server\Environment;
15
use Deployer\Task\Task as T;
16
use Deployer\Task\Context;
17
use Deployer\Task\GroupTask;
18
use Deployer\Type\Result;
19
use Monolog\Logger;
20
use Symfony\Component\Console\Question\ConfirmationQuestion;
21
use Symfony\Component\Console\Question\Question;
22
use Symfony\Component\Finder\Finder;
23
use Symfony\Component\Process\Exception\ProcessFailedException;
24
use Symfony\Component\Process\Process;
25
use Deployer\Cluster\ClusterFactory;
26
use Symfony\Component\Console\Input\InputArgument;
27
use Symfony\Component\Console\Input\InputInterface;
28
use Symfony\Component\Console\Input\InputOption;
29
use Symfony\Component\Console\Output\OutputInterface;
30
31
// There are two types of functions: Deployer dependent and Context dependent.
32
// Deployer dependent function uses in definition stage of recipe and may require Deployer::get() method.
33
// Context dependent function uses while task execution and must require only Context::get() method.
34
// But there is also a third type of functions: mixed. Mixed function uses in definition stage and in task
35
// execution stage. They are acts like two different function, but have same name. Example of such function
36
// is set() func. This function determine in which stage it was called by Context::get() method.
37
38
/**
39
 * @param string $name
40
 * @param string|null $host
41
 * @param int $port
42
 * @return BuilderInterface
43
 */
44
function server($name, $host = null, $port = 22)
45
{
46 2
    $deployer = Deployer::get();
47
48 2
    $env = new Environment();
49 2
    $config = new Configuration($name, $host, $port);
50
51 2
    if (get('ssh_type') === 'ext-ssh2') {
52 3
        $server = new Remote\SshExtension($config);
53 2
    } elseif (get('ssh_type') && get('ssh_type') === 'native') {
54
        $server = new Remote\NativeSsh($config);
55
    } else {
56 2
        $server = new Remote\PhpSecLib($config);
57
    }
58
59 2
    $deployer->servers->set($name, $server);
60 2
    $deployer->environments->set($name, $env);
61
62 2
    return new Builder($config, $env);
63
}
64
65
66
/**
67
 * @param string $name
68
 * @return BuilderInterface
69
 */
70
function localServer($name)
71
{
72 12
    $deployer = Deployer::get();
73
74 12
    $env = new Environment();
75 12
    $config = new Configuration($name, 'localhost'); // Builder requires server configuration.
76 12
    $server = new Local($config);
77
78 12
    $deployer->servers->set($name, $server);
79 12
    $deployer->environments->set($name, $env);
80
81 12
    return new Builder($config, $env);
82
}
83
84
/**
85
 * @param string $name Name of the cluster
86
 * @param array $nodes An array of nodes' host/ip
87
 * @param int $port Ssh port of the nodes
88
 *
89
 * Example:
90
 * You should pass a cluster name and nodes array.
91
 * Nodes array should be as following:
92
 * [ '192.168.1.1', 'example.com', '192.168.1.5' ]
93
 * @return BuilderInterface
94
 */
95
function cluster($name, $nodes, $port = 22)
96
{
97 2
    $deployer = Deployer::get();
98
99 2
    $cluster = ClusterFactory::create($deployer, $name, $nodes, $port);
100
101 3
    return $cluster->getBuilder();
102 13
}
103
104
105
/**
106
 * Load server list file.
107
 * @param string $file
108
 */
109
function serverList($file)
110
{
111 1
    $bootstrap = new Bootstrap\BootstrapByConfigFile();
112 1
    $bootstrap->setConfig($file);
113 1
    $bootstrap->parseConfig();
114 1
    $bootstrap->initServers();
115 7
    $bootstrap->initClusters();
116 1
}
117
118
/**
119
 * Set task description.
120
 *
121
 * @param string $title
122
 * @return string
123
 */
124
function desc($title = null)
125 3
{
126 15
    static $store = null;
127
128 15
    if ($title === null) {
129 15
        return $store;
130
    } else {
131 11
        return $store = $title;
132
    }
133
}
134
135
/**
136
 * Define a new task and save to tasks list.
137
 *
138
 * Alternatively get a defined task.
139
 *
140
 * @param string $name Name of current task.
141
 * @param callable|array|string|null $body Callable task, array of other tasks names or nothing to get a defined tasks
142
 * @return Task\Task
143
 * @throws \InvalidArgumentException
144
 */
145
function task($name, $body = null)
146
{
147 15
    $deployer = Deployer::get();
148
149 15
    if (empty($body)) {
150 15
        $task = $deployer->tasks->get($name);
151 2
        return $task;
152 1
    }
153
154 15
    if ($body instanceof \Closure) {
155 15
        $task = new T($name, $body);
156 15
    } elseif (is_array($body)) {
157 4
        $task = new GroupTask($name, $body);
158 4
    } elseif (is_string($body)) {
159
        $task = new T($name, function () use ($body) {
160
            run($body);
161
        });
162
    } else {
163
        throw new \InvalidArgumentException('Task should be an closure or array of other tasks.');
164
    }
165
166 15
    $deployer->tasks->set($name, $task);
167
168 15
    if (!empty(desc())) {
169 11
        $task->desc(desc());
170 11
        desc(''); // Clear title.
171 11
    }
172
173 15
    return $task;
174
}
175
176
/**
177
 * Call that task before specified task runs.
178
 *
179
 * @param string $it
180
 * @param string $that
181
 */
182
function before($it, $that)
183
{
184 2
    $deployer = Deployer::get();
185 2
    $beforeTask = $deployer->tasks->get($it);
186
187 2
    $beforeTask->addBefore($that);
188 2
}
189
190
/**
191
 * Call that task after specified task runs.
192
 *
193
 * @param string $it
194
 * @param string $that
195
 */
196
function after($it, $that)
197
{
198 2
    $deployer = Deployer::get();
199 2
    $afterTask = $deployer->tasks->get($it);
200
201 2
    $afterTask->addAfter($that);
202 2
}
203
204
/**
205
 * Setup which task run on failure of first.
206
 *
207
 * @param string $it
208
 * @param string $that
209
 */
210
function onFailure($it, $that)
211
{
212 11
    $deployer = Deployer::get();
213 11
    $deployer['onFailure']->set($it, $that);
214 11
}
215
216
/**
217
 * Add users arguments.
218
 *
219
 * Note what Deployer already has one argument: "stage".
220
 *
221
 * @param string $name
222
 * @param int $mode
223
 * @param string $description
224
 * @param mixed $default
225
 */
226
function argument($name, $mode = null, $description = '', $default = null)
227
{
228 11
    Deployer::get()->getConsole()->getUserDefinition()->addArgument(
229 11
        new InputArgument($name, $mode, $description, $default)
230 11
    );
231 11
}
232
233
/**
234
 * Add users options.
235
 *
236
 * @param string $name
237
 * @param string $shortcut
238
 * @param int $mode
239
 * @param string $description
240
 * @param mixed $default
241
 */
242
function option($name, $shortcut = null, $mode = null, $description = '', $default = null)
243
{
244 11
    Deployer::get()->getConsole()->getUserDefinition()->addOption(
245 11
        new InputOption($name, $shortcut, $mode, $description, $default)
246 11
    );
247 11
}
248
249
/**
250
 * Change the current working directory.
251
 *
252
 * @param string $path
253
 */
254
function cd($path)
255
{
256 3
    set('working_path', parse($path));
257 3
}
258
259
/**
260
 * Execute a callback within a specific directory and revert back to the initial working directory.
261
 *
262
 * @param string $path
263
 * @param callable $callback
264
 */
265
function within($path, $callback)
266
{
267
    $lastWorkingPath = workingPath();
268
    set('working_path', $path);
269
    $callback();
270
    set('working_path', $lastWorkingPath);
271
}
272
273
/**
274
 * Return the current working path.
275
 *
276
 * @return string
277
 */
278
function workingPath()
279
{
280 9
    return get('working_path', false);
281
}
282
283
/**
284
 * Run command on server.
285
 *
286
 * @param string $command
287
 * @return Result
288
 */
289
function run($command)
290
{
291 9
    $server = Context::get()->getServer();
292 9
    $serverName = $server->getConfiguration()->getName();
293 9
    $command = parse($command);
294 9
    $workingPath = workingPath();
295
296 9
    if (!empty($workingPath)) {
297 3
        $command = "cd $workingPath && ($command)";
298 3
    }
299
300 9
    if (isVeryVerbose()) {
301
        writeln("[$serverName] <fg=red>></fg=red> $command");
302
    }
303
304 9
    logger("[$serverName] > $command");
305
306 9
    if ($server instanceof Local) {
307
        $output = $server->mustRun($command, function ($type, $buffer) use ($serverName) {
308 9 View Code Duplication
            if (isDebug()) {
309
                output()->writeln(array_map(function ($line) use ($serverName) {
310
                    return output()->isDecorated()
311
                        ? "[$serverName] \033[1;30m< $line\033[0m"
312
                        : "[$serverName] < $line";
313
                }, explode("\n", rtrim($buffer))), OutputInterface::OUTPUT_RAW);
314
            }
315 9
        });
316 9
    } else {
317
        $output = $server->run($command);
318 View Code Duplication
        if (isDebug() && !empty($output)) {
319
            output()->writeln(array_map(function ($line) use ($serverName) {
320
                return output()->isDecorated()
321
                    ? "[$serverName] \033[1;30m< $line\033[0m"
322
                    : "[$serverName] < $line";
323
            }, explode("\n", rtrim($output))), OutputInterface::OUTPUT_RAW);
324
        }
325
    }
326
327 9
    if (!empty(rtrim($output))) {
328 9
        logger("[$serverName] < $output");
329 9
    }
330
331 9
    return new Result($output);
332
}
333
334
/**
335
 * Execute commands on local machine.
336
 * @param string $command Command to run locally.
337
 * @param int $timeout (optional) Override process command timeout in seconds.
338
 * @return Result Output of command.
339
 * @throws \RuntimeException
340
 */
341
function runLocally($command, $timeout = 300)
342
{
343 5
    $command = parse($command);
344
345 5
    if (isVeryVerbose()) {
346
        writeln("[localhost] <fg=red>></fg=red> : $command");
347
    }
348
349 5
    logger("[localhost] > $command");
350
351 5
    $process = new Process($command);
352 5
    $process->setTimeout($timeout);
353
    $process->run(function ($type, $buffer) {
354 4
        if (isDebug()) {
355
            if ('err' === $type) {
356
                write("<fg=red>></fg=red> $buffer");
357
            } else {
358
                write("<fg=green>></fg=green> $buffer");
359
            }
360
        }
361 5
    });
362
363 5
    if (!$process->isSuccessful()) {
364
        throw new ProcessFailedException($process);
365
    }
366
367 5
    $output = $process->getOutput();
368
369 5
    logger("[localhost] < $output");
370
371 5
    return new Result($output);
372
}
373
374
/**
375
 * Run test command.
376
 * Example:
377
 *
378
 *     test('[ -d {{release_path}} ]')
379
 *
380
 * @param string $command
381
 * @return bool
382
 */
383
function test($command)
384
{
385 2
    return run("if $command; then echo 'true'; fi")->toBool();
386
}
387
388
/**
389
 * Run test command locally.
390
 * Example:
391
 *
392
 *     testLocally('[ -d {{local_release_path}} ]')
393
 *
394
 * @param string $command
395
 * @return bool
396
 */
397
function testLocally($command)
398
{
399
    return runLocally("if $command; then echo 'true'; fi")->toBool();
400
}
401
402
/**
403
 * Upload file or directory to current server.
404
 * @param string $local
405
 * @param string $remote
406
 * @throws \RuntimeException
407
 */
408
function upload($local, $remote)
409
{
410 1
    $server = Context::get()->getServer();
411 1
    $local = parse($local);
412 1
    $remote = parse($remote);
413
414 1
    if (is_file($local)) {
415 1
        writeln("Upload file <info>$local</info> to <info>$remote</info>");
416
417 1
        $server->upload($local, $remote);
418 1
    } elseif (is_dir($local)) {
419 1
        writeln("Upload from <info>$local</info> to <info>$remote</info>");
420
421 1
        $finder = new Finder();
422
        $files = $finder
423 1
            ->files()
424 1
            ->ignoreUnreadableDirs()
425 1
            ->ignoreVCS(true)
426 1
            ->ignoreDotFiles(false)
427 1
            ->in($local);
428
429
        /** @var $file \Symfony\Component\Finder\SplFileInfo */
430 1
        foreach ($files as $file) {
431 1
            if (isDebug()) {
432
                writeln("Uploading <info>{$file->getRealPath()}</info>");
433
            }
434
435 1
            $server->upload(
436 1
                $file->getRealPath(),
437 1
                $remote . '/' . $file->getRelativePathname()
438 1
            );
439 1
        }
440 1
    } else {
441
        throw new \RuntimeException("Uploading path '$local' does not exist.");
442
    }
443 1
}
444
445
/**
446
 * Download file from remote server.
447
 *
448
 * @param string $local
449
 * @param string $remote
450
 */
451
function download($local, $remote)
452
{
453 2
    $server = Context::get()->getServer();
454 2
    $local = parse($local);
455 2
    $remote = parse($remote);
456
457 2
    writeln("Download file <info>$remote</info> to <info>$local</info>");
458 2
    $server->download($local, $remote);
459 2
}
460
461
/**
462
 * Writes a message to the output and adds a newline at the end.
463
 * @param string|array $message
464
 */
465
function writeln($message)
466
{
467 6
    output()->writeln($message);
468 6
}
469
470
/**
471
 * Writes a message to the output.
472
 * @param string $message
473
 */
474
function write($message)
475
{
476
    output()->write($message);
477
}
478
479
/**
480
 * @param string $message
481
 * @param int $level
482
 */
483
function logger($message, $level = Logger::DEBUG)
484
{
485 13
    if (is_array($message)) {
486
        $message = join("\n", $message);
487
    }
488
489 13
    Deployer::get()->getLogger()->log($level, $message);
490 13
}
491
492
/**
493
 * Setup configuration option.
494
 *
495
 * @param string $name
496
 * @param mixed $value
497
 */
498
function set($name, $value)
499
{
500 11
    if (Context::get() === false) {
501 11
        Deployer::setDefault($name, $value);
502 11
    } else {
503 3
        Context::get()->getEnvironment()->set($name, $value);
504
    }
505 11
}
506
507
/**
508
 * Merge new config params to existing config array.
509
 *
510
 * @param string $name
511
 * @param array $array
512
 */
513
function add($name, $array)
514
{
515
    if (Context::get() === false) {
516
        Deployer::addDefault($name, $array);
517
    } else {
518
        Context::get()->getEnvironment()->add($name, $array);
519
    }
520
}
521
522
/**
523
 * Get configuration value.
524
 *
525
 * @param string $name
526
 * @param mixed|null $default
527
 * @return mixed
528
 */
529
function get($name, $default = null)
530
{
531 16
    if (Context::get() === false) {
532 14
        return Deployer::getDefault($name, $default);
533
    } else {
534 11
        return Context::get()->getEnvironment()->get($name, $default);
535
    }
536
}
537
538
/**
539
 * Check if there is such configuration option.
540
 *
541
 * @param string $name
542
 * @return boolean
543
 */
544
function has($name)
545
{
546 4
    if (Context::get() === false) {
547 2
        return Deployer::hasDefault($name);
548
    } else {
549 2
        return Context::get()->getEnvironment()->has($name);
550
    }
551
}
552
553
/**
554
 * @param string $message
555
 * @param string|null $default
556
 * @param string[]|null $suggestedChoices
557
 * @return string
558
 * @codeCoverageIgnore
559
 */
560
function ask($message, $default = null, $suggestedChoices = null)
561
{
562
    if (($suggestedChoices !== null) && (empty($suggestedChoices))) {
563
        throw new \InvalidArgumentException('Suggested choices should not be empty');
564
    }
565
566
    if (isQuiet()) {
567
        return $default;
568
    }
569
570
    $helper = Deployer::get()->getHelper('question');
571
572
    $message = "<question>$message" . (($default === null) ? "" : " [$default]") . "</question> ";
573
574
    $question = new Question($message, $default);
575
576
    if (empty($suggestedChoices) === false) {
577
        $question->setAutocompleterValues($suggestedChoices);
578
    }
579
580
    return $helper->ask(input(), output(), $question);
581
}
582
583
/**
584
 * @param string $message
585
 * @param bool $default
586
 * @return bool
587
 * @codeCoverageIgnore
588
 */
589
function askConfirmation($message, $default = false)
590
{
591
    if (isQuiet()) {
592
        return $default;
593
    }
594
595
    $helper = Deployer::get()->getHelper('question');
596
597
    $yesOrNo = $default ? 'Y/n' : 'y/N';
598
    $message = "<question>$message [$yesOrNo]</question> ";
599
600
    $question = new ConfirmationQuestion($message, $default);
601
602
    return $helper->ask(input(), output(), $question);
603
}
604
605
/**
606
 * @param string $message
607
 * @return string
608
 * @codeCoverageIgnore
609
 */
610
function askHiddenResponse($message)
611
{
612
    if (isQuiet()) {
613
        return '';
614
    }
615
616
    $helper = Deployer::get()->getHelper('question');
617
618
    $message = "<question>$message</question> ";
619
620
    $question = new Question($message);
621
    $question->setHidden(true);
622
    $question->setHiddenFallback(false);
623
624
    return $helper->ask(input(), output(), $question);
625
}
626
627
/**
628
 * @return InputInterface
629
 */
630
function input()
631
{
632
    return Context::get()->getInput();
633
}
634
635
636
/**
637
 * @return OutputInterface
638
 */
639
function output()
640
{
641 16
    return Context::get()->getOutput();
642
}
643
644
/**
645
 * @return bool
646
 */
647
function isQuiet()
648
{
649
    return OutputInterface::VERBOSITY_QUIET === output()->getVerbosity();
650
}
651
652
653
/**
654
 * @return bool
655
 */
656
function isVerbose()
657
{
658
    return OutputInterface::VERBOSITY_VERBOSE <= output()->getVerbosity();
659
}
660
661
662
/**
663
 * @return bool
664
 */
665
function isVeryVerbose()
666
{
667 13
    return OutputInterface::VERBOSITY_VERY_VERBOSE <= output()->getVerbosity();
668
}
669
670
671
/**
672
 * @return bool
673
 */
674
function isDebug()
675
{
676 14
    return OutputInterface::VERBOSITY_DEBUG <= output()->getVerbosity();
677
}
678
679
/**
680
 * Deprecated, use set()/get().
681
 * @deprecated
682
 */
683
function env()
684
{
685
    throw new \RuntimeException('env() function deprecated. Please, use set() or get() instead of.');
686
}
687
688
/**
689
 * Check if command exist in bash.
690
 *
691
 * @param string $command
692
 * @return bool
693
 */
694
function commandExist($command)
695
{
696
    return run("if hash $command 2>/dev/null; then echo 'true'; fi")->toBool();
697
}
698
699
/**
700
 * Parse set values.
701
 *
702
 * @param string $value
703
 * @return string
704
 */
705
function parse($value)
706
{
707 16
    return Context::get()->getEnvironment()->parse($value);
708
}
709