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 — master ( 433f91...1b7dfd )
by Greg
04:50
created

SecureShell::_initialize()   B

Complexity

Conditions 6
Paths 12

Size

Total Lines 16
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 16
rs 8.8571
cc 6
eloc 9
nc 12
nop 0
1
<?php
2
namespace Codeception\Extension;
3
4
use Codeception\Exception\ModuleException;
5
use Codeception\Exception\ModuleConfigException;
6
use Codeception\Module;
7
use Codeception\Configuration;
8
use \SplFileObject;
9
use \RuntimeException;
10
use \Exception;
11
12
class SecureShell extends Module
13
{
14
15
    const DEFAULT_PORT  = 22;
16
    const AUTH_PASSWORD = 1;
17
    const AUTH_PUBKEY   = 2;
18
    const AUTH_HOSTKEY  = 3;
19
    const AUTH_AGENT    = 4;
20
    const AUTH_NONE     = 0;
21
22
    protected $config = ['StrictHostKeyChecking', 'KnownHostsFile'];
23
24
    protected $requiredFields = [];
25
26
    protected static $knownHostsFile = '';
27
28
    protected static $strictHostKeyChecking = false;
29
30
    protected $connection;
31
32
    private $output;
33
34
    public function _initialize()
35
    {
36
        if (isset($this->config['StrictHostKeyChecking'])) {
37
            static::$strictHostKeyChecking = (bool) $this->config['StrictHostKeyChecking'];
38
        }
39
        if (isset($this->config['KnownHostsFile'])) {
40
            static::$knownHostsFile = $this->config['KnownHostsFile'];
41
        } elseif (static::$strictHostKeyChecking) {
42
            // default KnownHostsFile if StrictHostKeyChecking enabled
43
            static::$knownHostsFile = Configuration::projectDir() . 'known_hosts';
44
        }
45
        // check that a KnownHostsFile exists if StrictHostKeyChecking enabled
46
        if (static::$strictHostKeyChecking && !file_exists(static::$knownHostsFile)) {
47
            throw new ModuleConfigException(get_class($this), 'KnownHostsFile "' . static::$knownHostsFile . '" not found');
48
        }
49
    }
50
51
    public function openConnection($host,
52
                                    $port = SecureShell::DEFAULT_PORT,
53
                                    $auth = SecureShell::AUTH_PASSWORD,
54
                                    ...$args)
55
    {
56
        $callbacks = array('disconnect' => [$this, '_disconnect']);
57
58
        try {
59
            $connection = ssh2_connect($host, $port, $callbacks);
60
            if (!$connection) {
61
                throw new ModuleException(get_class($this), "Unable to connect to {$host} on port {$port}");
62
            } else {
63
                $this->__checkFingerprint($connection);
64
65
                if ($this->__authenticate($connection, $auth, ...$args) === false) {
66
                    throw new ModuleException(get_class($this), "Authentication failed on server {$host}:{$port}");
67
                } else {
68
                    $this->connection = $connection;
69
                }
70
            }
71
        } catch (ModuleException $e) {
72
            throw $e;
73
        } catch (Exception $e) {
74
            throw new ModuleException(get_class($this), $e->getMessage());
75
        }
76
        return $this->connection;
77
    }
78
79
    public function closeConnection() {
80
        $this->connection = null;
81
        return true;
82
    }
83
84
    public function getConnection() {
85
        return $this->connection;
86
    }
87
88
    protected function __authenticate($connection, $method, ...$args)
89
    {
90
        switch ($method) {
91
            case SecureShell::AUTH_PASSWORD:
92
                return ssh2_auth_password($connection, ...$args);
93
            case SecureShell::AUTH_PUBKEY:
94
                return ssh2_auth_pubkey_file($connection, ...$args);
95
            case SecureShell::AUTH_HOSTKEY:
96
                return ssh2_auth_hostbased_file($connection, ...$args);
97
            case SecureShell::AUTH_AGENT:
98
                return ssh2_auth_agent($connection, ...$args);
99
            case SecureShell::AUTH_NONE:
100
                return ssh2_auth_none($connection, ...$args);
101
            default:
102
                throw new ModuleException(get_class($this), 'Unsupported authentication method');
103
        }
104
    }
105
106
    protected function __checkFingerprint($connection)
107
    {
108
        $knownHost = false;
109
        try {
110
            $fingerprint = ssh2_fingerprint($connection, SSH2_FINGERPRINT_MD5);
111
            if (file_exists(static::$knownHostsFile)){
112
                $file = new SplFileObject(static::$knownHostsFile);
113
                $file->setFlags(SplFileObject::READ_CSV);
114
                $file->setCsvControl(' ');
115
                foreach ($file as $entry) {
116
                    list(, $fp,,) = $entry;
117
                    $fp = preg_replace('/(?:MD5)?:/', '', $fp);
118
                    $knownHost = (strcasecmp($fp, $fingerprint) === 0);
119
                    if ($knownHost) {
120
                        break;
121
                    }
122
                }
123
            }
124
            $knownHost = $knownHost || !static::$strictHostKeyChecking;
125
126
            if ($knownHost === false) {
127
                throw new ModuleException(get_class($this), 'Unable to verify server identity!');
128
            }
129
        } catch (RuntimeException $e) {
130
            if (static::$strictHostKeyChecking) {
131
                throw new ModuleException(get_class($this), 'Unable to verify server identity!');
132
            }
133
        }
134
        return $fingerprint;
135
    }
136
137
    /** Remote Commands methods **/
138
139
    public function runRemoteCommand($command)
140
    {
141
        try {
142
            $stream = ssh2_exec($this->connection, $command);
143
            stream_set_blocking($stream, true);
144
            $errStream = ssh2_fetch_stream($stream, SSH2_STREAM_STDERR);
145
            $this->output['STDOUT'] = stream_get_contents($stream);
146
            $this->output['STDERR'] = stream_get_contents($errStream);
147
            return $this->output;
148
        } catch (Exception $e) {
149
            throw new ModuleException(get_class($this), $e->getMessage());
150
        }
151
    }
152
153
    public function seeInRemoteOutput($text)
154
    {
155
        \PHPUnit_Framework_Assert::assertContains($text, $this->output['STDOUT']);
156
    }
157
158
    public function dontSeeInRemoteOutput($text)
159
    {
160
        \PHPUnit_Framework_Assert::assertNotContains($text, $this->output['STDOUT']);
161
    }
162
163
    /** Remote Files methods **/
164
165
    public function seeRemoteFile($filename)
166
    {
167
        $sftp = ssh2_sftp($this->connection);
168
        $res = ssh2_sftp_stat($sftp, $filename);
169
        \PHPUnit_Framework_Assert::assertNotEmpty($res);
170
    }
171
172
    public function dontSeeRemoteFile($filename)
173
    {
174
        $sftp = ssh2_sftp($this->connection);
175
        try {
176
            $res = (bool) ssh2_sftp_stat($sftp, $filename);
177
        } catch (Exception $e) {
178
            $res = false;
179
        }
180
        \PHPUnit_Framework_Assert::assertFalse($res);
181
    }
182
183
    public function grabRemoteFile($filename)
184
    {
185
        try {
186
            $sftp = ssh2_sftp($this->connection);
187
            return file_get_contents("ssh2.sftp://{$sftp}/{$filename}");
188
        } catch (Exception $e) {
189
            throw new ModuleException(get_class($this), $e->getMessage());
190
        }
191
    }
192
193
    /** Remote Dir methods **/
194
195 View Code Duplication
    public function seeRemoteDir($dirname)
1 ignored issue
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
196
    {
197
        try {
198
            $res = (bool) $this->grabRemoteDir($dirname);
199
        } catch (Exception $e) {
200
            $res = false;
201
        }
202
        \PHPUnit_Framework_Assert::assertTrue($res);
203
    }
204
205 View Code Duplication
    public function dontSeeRemoteDir($dirname)
1 ignored issue
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
206
    {
207
        try {
208
            $res = (bool) $this->grabRemoteDir($dirname);
209
        } catch (Exception $e) {
210
            $res = false;
211
        }
212
        \PHPUnit_Framework_Assert::assertFalse($res);
213
    }
214
215
    public function grabRemoteDir($dirname)
216
    {
217
        $res = null;
218
        try {
219
            $sftp = ssh2_sftp($this->connection);
220
            $res = scandir("ssh2.sftp://{$sftp}/{$dirname}");
221
        } catch (Exception $e) {
222
            throw new ModuleException(get_class($this), $e->getMessage());
223
        }
224
        return $res;
225
    }
226
227
}
228