Skip to content

Commit c4c4f4e

Browse files
committed
Added wait and other methods
1 parent bd54feb commit c4c4f4e

File tree

1 file changed

+63
-16
lines changed

1 file changed

+63
-16
lines changed

src/Shell/Shell.php

+63-16
Original file line numberDiff line numberDiff line change
@@ -11,20 +11,21 @@
1111

1212
class Shell {
1313

14-
const STDIN = 0;
15-
const STDOUT = 1;
16-
const STDERR = 2;
14+
const STDIN_DESCRIPTOR_KEY = 0;
15+
const STDOUT_DESCRIPTOR_KEY = 1;
16+
const STDERR_DESCRIPTOR_KEY = 2;
1717

1818
protected $command;
1919
protected $cwd;
2020
protected $descriptors;
2121
protected $env;
22+
protected $error;
2223
protected $input;
2324
protected $output;
2425
protected $pipes;
2526
protected $process;
27+
protected $startTime;
2628
protected $status;
27-
protected $error;
2829
protected $timeout;
2930

3031
public function __construct(string $command, string $cwd = null, $input = null, $env = null, $timeout = 60)
@@ -35,29 +36,43 @@ public function __construct(string $command, string $cwd = null, $input = null,
3536

3637
$this->command = $command;
3738
$this->cwd = $cwd;
38-
$this->descriptors = $this->getDescriptors();
3939
$this->env = $env;
4040
$this->input = $input;
4141
$this->timeout = $timeout;
4242
}
4343

4444
public function execute()
4545
{
46-
$descriptors = $this->getDescriptors();
46+
$this->start();
47+
$this->wait();
48+
}
49+
50+
public function start()
51+
{
52+
if ($this->isRunning()) {
53+
throw new RuntimeException('Process is already running');
54+
}
4755

48-
$this->process = proc_open($this->command, $descriptors, $this->pipes, $this->cwd, $this->env);
56+
$this->descriptors = $this->getDescriptors();
57+
58+
$this->process = proc_open($this->command, $this->descriptors, $this->pipes, $this->cwd, $this->env);
4959

5060
if (!\is_resource($this->process)) {
5161
throw new RuntimeException('Bad program could not be started.');
5262
}
63+
64+
$this->setInput();
65+
66+
$this->startTime = microtime(true);
67+
$this->status = $this->updateStatus();
5368
}
5469

5570
public function getDescriptors()
5671
{
5772
return array(
58-
self::STDIN => array("pipe", "r"),
59-
self::STDOUT => array("pipe", "w"),
60-
self::STDERR => array("pipe", "r")
73+
self::STDIN_DESCRIPTOR_KEY => array("pipe", "r"),
74+
self::STDOUT_DESCRIPTOR_KEY => array("pipe", "w"),
75+
self::STDERR_DESCRIPTOR_KEY => array("pipe", "r")
6176
);
6277
}
6378

@@ -70,28 +85,60 @@ public function getOutput()
7085
{
7186
$this->output = stream_get_contents($this->pipes[1]);
7287

73-
7488
return $this->output;
7589
}
7690

77-
public function getStatus()
91+
public function getErrorOutput()
92+
{
93+
$this->error = stream_get_contents($this->pipes[2]);
94+
95+
return $this->error;
96+
}
97+
98+
public function checkTimeout()
99+
{
100+
if ($this->timeout && $this->timeout < microtime(true) - $this->startTime) {
101+
$this->stop();
102+
}
103+
104+
return $this->status;
105+
}
106+
107+
public function updateStatus()
78108
{
79109
$this->status = proc_get_status($this->process);
110+
111+
if (!$this->isRunning()) {
112+
$this->stop();
113+
}
114+
80115
return $this->status;
81116
}
82117

83-
public function getErrorOutput()
118+
public function wait()
84119
{
85-
$this->error = stream_get_contents($this->pipes[2]);
86-
return $this->error;
120+
while ($this->isRunning()) {
121+
usleep(1000);
122+
$this->checkTimeout();
123+
$this->updateStatus();
124+
}
125+
126+
return $this->status;
127+
}
128+
129+
public function isRunning()
130+
{
131+
return $this->status['running'];
87132
}
88133

89134
public function stop()
90135
{
91136
fclose($this->pipes[0]);
92137
fclose($this->pipes[1]);
93138
fclose($this->pipes[2]);
94-
return proc_close($this->process);
139+
proc_close($this->process);
140+
141+
return $this->status;
95142
}
96143

97144
public function kill()

0 commit comments

Comments
 (0)