Completed
Push — master ( e0e3f0...3077c0 )
by Sébastien
04:19
created

VideoInfoService::__construct()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
eloc 1
dl 0
loc 3
ccs 2
cts 2
cp 1
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 1
crap 1
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Soluble\MediaTools;
6
7
use Soluble\MediaTools\Config\FFProbeConfigInterface;
8
use Soluble\MediaTools\Exception\FileNotFoundException;
9
use Soluble\MediaTools\Util\Assert\PathAssertionsTrait;
10
use Soluble\MediaTools\Video\Exception\InfoExceptionInterface;
11
use Soluble\MediaTools\Video\Exception\InfoProcessExceptionInterface;
12
use Soluble\MediaTools\Video\Exception\MissingInputFileException;
13
use Soluble\MediaTools\Video\Exception\ProcessFailedException;
14
use Soluble\MediaTools\Video\Exception\RuntimeException;
15
use Soluble\MediaTools\Video\Info;
16
use Soluble\MediaTools\Video\InfoServiceInterface;
17
use Symfony\Component\Process\Exception as SPException;
18
use Symfony\Component\Process\Process;
19
20
class VideoInfoService implements InfoServiceInterface
21
{
22
    use PathAssertionsTrait;
23
24
    /** @var FFProbeConfigInterface */
25
    protected $ffprobeConfig;
26
27 2
    public function __construct(FFProbeConfigInterface $ffProbeConfig)
28
    {
29 2
        $this->ffprobeConfig = $ffProbeConfig;
30 2
    }
31
32
    /**
33
     * Return ready-to-run symfony process object that you can use
34
     * to `run()` or `start()` programmatically. Useful if you want to make
35
     * things your way...
36
     *
37
     * @see https://symfony.com/doc/current/components/process.html
38
     *
39
     * @throws FileNotFoundException when inputFile does not exists
40
     */
41 1
    public function getFFProbeProcess(string $inputFile): Process
42
    {
43 1
        $ffprobeCmd = trim(sprintf(
44 1
            '%s %s %s',
45 1
            $this->ffprobeConfig->getBinary(),
46 1
            implode(' ', [
47 1
                '-v quiet',
48
                '-print_format json',
49
                '-show_format',
50
                '-show_streams',
51
            ]),
52 1
            sprintf('-i %s', escapeshellarg($inputFile))
53
        ));
54
55 1
        $process = new Process($ffprobeCmd);
56 1
        $process->setTimeout($this->ffprobeConfig->getTimeout());
57 1
        $process->setIdleTimeout($this->ffprobeConfig->getIdleTimeout());
58 1
        $process->setEnv($this->ffprobeConfig->getEnv());
59
60 1
        return $process;
61
    }
62
63
    /**
64
     * @throws InfoExceptionInterface
65
     * @throws InfoProcessExceptionInterface
66
     * @throws ProcessFailedException
67
     * @throws MissingInputFileException
68
     * @throws RuntimeException
69
     */
70 2
    public function getInfo(string $file): Info
71
    {
72
        try {
73 2
            $this->ensureFileExists($file);
74 1
            $process = $this->getFFProbeProcess($file);
75
76 1
            $process->mustRun();
77 1
            $output = $process->getOutput();
78 1
        } catch (FileNotFoundException $e) {
79 1
            throw new MissingInputFileException($e->getMessage());
80
        } catch (SPException\ProcessFailedException | SPException\ProcessTimedOutException | SPException\ProcessSignaledException $e) {
81
            throw new ProcessFailedException($e->getProcess(), $e);
82
        } catch (SPException\RuntimeException $e) {
83
            throw new RuntimeException($e->getMessage());
84
        }
85
86 1
        return Info::createFromFFProbeJson($file, $output);
87
    }
88
}
89