GitVersionControl::runCommand()   A
last analyzed

Complexity

Conditions 3
Paths 2

Size

Total Lines 11
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 7
CRAP Score 3

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 11
ccs 7
cts 7
cp 1
rs 9.4285
cc 3
eloc 7
nc 2
nop 2
crap 3
1
<?php
2
3
/**
4
 * Moodle component manager.
5
 *
6
 * @author Luke Carrier <[email protected]>
7
 * @copyright 2016 Luke Carrier
8
 * @license GPL-3.0+
9
 */
10
11
namespace ComponentManager\VersionControl\Git;
12
13
use ComponentManager\Exception\VersionControlException;
14
use ComponentManager\VersionControl\Git\Command\CheckoutCommand;
15
use ComponentManager\VersionControl\Git\Command\CheckoutIndexCommand;
16
use ComponentManager\VersionControl\Git\Command\Command;
17
use ComponentManager\VersionControl\Git\Command\FetchCommand;
18
use ComponentManager\VersionControl\Git\Command\InitCommand;
19
use ComponentManager\VersionControl\Git\Command\RevParseCommand;
20
use ComponentManager\VersionControl\Git\Command\RemoteAddCommand;
21
use Symfony\Component\Process\Process;
22
use Symfony\Component\Process\ProcessBuilder;
23
24
/**
25
 * Git version control.
26
 */
27
class GitVersionControl {
28
    /**
29
     * The repository's on-disk location.
30
     *
31
     * @var string
32
     */
33
    protected $directory;
34
35
    /**
36
     * Git executable.
37
     *
38
     * @var string
39
     */
40
    protected $gitExecutable;
41
42
    /**
43
     * Process timeout.
44
     *
45
     * @var integer|null
46
     */
47
    protected $timeout;
48
49
    /**
50
     * Remotes.
51
     *
52
     * @var GitRemote[]
53
     */
54
    protected $remotes;
55
56
    /**
57
     * Initialiser.
58
     *
59
     * @param string       $gitExecutable
60
     * @param string       $directory
61
     * @param integer|null $timeout
0 ignored issues
show
Documentation introduced by
Consider making the type for parameter $timeout a bit more specific; maybe use integer.
Loading history...
62
     */
63 3
    public function __construct($gitExecutable, $directory, $timeout=60) {
64 3
        $this->gitExecutable = $gitExecutable;
65 3
        $this->timeout       = $timeout;
66
67 3
        $this->directory = $directory;
68 3
        $this->remotes   = [];
69 3
    }
70
71
    /**
72
     * Get a ready-to-run Process instance.
73
     *
74
     * @param string[] $arguments Arguments to pass to the Git binary.
75
     *
76
     * @return Process
77
     */
78 3
    public function createProcess($arguments) {
79 3
        array_unshift($arguments, $this->gitExecutable);
80
81 3
        $builder = new ProcessBuilder($arguments);
82 3
        $builder->setTimeout($this->timeout);
83 3
        $builder->setWorkingDirectory($this->directory);
84
85 3
        return $builder->getProcess();
86
    }
87
88
    /**
89
     * Execute and ensure successful execution of a command.
90
     *
91
     * @param Command $command
92
     * @param integer|null $exceptionCode
93
     *
94
     * @return Process
95
     *
96
     * @throws VersionControlException
97
     */
98 2
    public function runCommand(Command $command, $exceptionCode=null) {
99 2
        $process = $this->createProcess($command->getCommandLine());
100 2
        $process->run();
101
102 2
        if ($exceptionCode !== null && !$process->isSuccessful()) {
103 1
            throw new VersionControlException(
104 1
                $process->getCommandLine(), $exceptionCode);
105
        }
106
107 1
        return $process;
108
    }
109
110
    /**
111
     * Add the specified remote to the repository.
112
     *
113
     * @param GitRemote $remote
114
     *
115
     * @return Process
116
     *
117
     * @throws VersionControlException
118
     *
119
     * @codeCoverageIgnore
120
     */
121
    public function addRemote(GitRemote $remote) {
122
        $command = new RemoteAddCommand($remote);
123
        return $this->runCommand($command,
124
                VersionControlException::CODE_REMOTE_ADD_FAILED);
125
    }
126
127
    /**
128
     * Checkout the specified reference.
129
     *
130
     * @param string $ref
131
     *
132
     * @return Process
133
     *
134
     * @throws VersionControlException
135
     *
136
     * @codeCoverageIgnore
137
     */
138
    public function checkout($ref) {
139
        $command = new CheckoutCommand($ref);
140
        return $this->runCommand(
141
                $command, VersionControlException::CODE_CHECKOUT_FAILED);
142
    }
143
144
    /**
145
     * Checkout all files in the index to the specified directory.
146
     *
147
     * @param string $prefix
148
     *
149
     * @return Process
150
     *
151
     * @throws VersionControlException
152
     *
153
     * @codeCoverageIgnore
154
     */
155
    public function checkoutIndex($prefix) {
156
        $command = new CheckoutIndexCommand($prefix);
157
        return $this->runCommand(
158
                $command, VersionControlException::CODE_CHECKOUT_INDEX_FAILED);
159
    }
160
161
    /**
162
     * Fetch references from the specified remote.
163
     *
164
     * @param string|null $remote
165
     *
166
     * @return Process
167
     *
168
     * @throws VersionControlException
169
     *
170
     * @codeCoverageIgnore
171
     */
172
    public function fetch($remote=null) {
173
        $command = new FetchCommand($remote);
174
        return $this->runCommand(
175
                $command, VersionControlException::CODE_FETCH_FAILED);
176
    }
177
178
    /**
179
     * Fetch tags from the specified remote.
180
     *
181
     * @param string|null $remote
182
     *
183
     * @return Process
184
     *
185
     * @throws VersionControlException
186
     *
187
     * @codeCoverageIgnore
188
     */
189
    public function fetchTags($remote=null) {
190
        $command = new FetchCommand($remote);
191
        $command->setTags(true);
192
        return $this->runCommand(
193
                $command, VersionControlException::CODE_FETCH_FAILED);
194
    }
195
196
    /**
197
     * Initialise Git repository.
198
     *
199
     * @throws VersionControlException
200
     *
201
     * @codeCoverageIgnore
202
     */
203
    public function init() {
204
        $command = new InitCommand();
205
        return $this->runCommand($command);
206
    }
207
208
    /**
209
     * Get the commit hash for the specified ref.
210
     *
211
     * @param string $ref
212
     *
213
     * @return Process
214
     *
215
     * @throws VersionControlException
216
     *
217
     * @codeCoverageIgnore
218
     */
219
    public function parseRevision($ref) {
220
        $command = new RevParseCommand($ref);
221
        return $this->runCommand(
222
                $command, VersionControlException::CODE_REV_PARSE_FAILED);
223
    }
224
}
225