• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

PHPCSStandards / PHP_CodeSniffer / 15253296250

26 May 2025 11:55AM UTC coverage: 78.632% (+0.3%) from 78.375%
15253296250

Pull #1105

github

web-flow
Merge d9441d98f into caf806050
Pull Request #1105: Skip tests when 'git' command is not available

19665 of 25009 relevant lines covered (78.63%)

88.67 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.0
/src/Files/FileList.php
1
<?php
2
/**
3
 * Represents a list of files on the file system that are to be checked during the run.
4
 *
5
 * File objects are created as needed rather than all at once.
6
 *
7
 * @author    Greg Sherwood <gsherwood@squiz.net>
8
 * @copyright 2006-2015 Squiz Pty Ltd (ABN 77 084 670 600)
9
 * @license   https://github.com/PHPCSStandards/PHP_CodeSniffer/blob/master/licence.txt BSD Licence
10
 */
11

12
namespace PHP_CodeSniffer\Files;
13

14
use Countable;
15
use FilesystemIterator;
16
use Iterator;
17
use PHP_CodeSniffer\Autoload;
18
use PHP_CodeSniffer\Config;
19
use PHP_CodeSniffer\Exceptions\DeepExitException;
20
use PHP_CodeSniffer\Ruleset;
21
use PHP_CodeSniffer\Util\Common;
22
use PHP_CodeSniffer\Util\ExitCode;
23
use RecursiveArrayIterator;
24
use RecursiveDirectoryIterator;
25
use RecursiveIteratorIterator;
26
use ReturnTypeWillChange;
27

28
class FileList implements Iterator, Countable
29
{
30

31
    /**
32
     * A list of file paths that are included in the list.
33
     *
34
     * @var array
35
     */
36
    private $files = [];
37

38
    /**
39
     * The number of files in the list.
40
     *
41
     * @var integer
42
     */
43
    private $numFiles = 0;
44

45
    /**
46
     * The config data for the run.
47
     *
48
     * @var \PHP_CodeSniffer\Config
49
     */
50
    public $config = null;
51

52
    /**
53
     * The ruleset used for the run.
54
     *
55
     * @var \PHP_CodeSniffer\Ruleset
56
     */
57
    public $ruleset = null;
58

59
    /**
60
     * An array of patterns to use for skipping files.
61
     *
62
     * @var array
63
     */
64
    protected $ignorePatterns = [];
65

66

67
    /**
68
     * Constructs a file list and loads in an array of file paths to process.
69
     *
70
     * @param \PHP_CodeSniffer\Config  $config  The config data for the run.
71
     * @param \PHP_CodeSniffer\Ruleset $ruleset The ruleset used for the run.
72
     *
73
     * @return void
74
     */
75
    public function __construct(Config $config, Ruleset $ruleset)
×
76
    {
77
        $this->ruleset = $ruleset;
×
78
        $this->config  = $config;
×
79

80
        $paths = $config->files;
×
81
        foreach ($paths as $path) {
×
82
            $isPharFile = Common::isPharFile($path);
×
83
            if (is_dir($path) === true || $isPharFile === true) {
×
84
                if ($isPharFile === true) {
×
85
                    $path = 'phar://'.$path;
×
86
                }
87

88
                $filterClass = $this->getFilterClass();
×
89

90
                $di       = new RecursiveDirectoryIterator($path, (RecursiveDirectoryIterator::SKIP_DOTS | FilesystemIterator::FOLLOW_SYMLINKS));
×
91
                $filter   = new $filterClass($di, $path, $config, $ruleset);
×
92
                $iterator = new RecursiveIteratorIterator($filter);
×
93

94
                foreach ($iterator as $file) {
×
95
                    $this->files[$file->getPathname()] = null;
×
96
                    $this->numFiles++;
×
97
                }
98
            } else {
99
                $this->addFile($path);
×
100
            }//end if
101
        }//end foreach
102

103
        reset($this->files);
×
104

105
    }//end __construct()
106

107

108
    /**
109
     * Add a file to the list.
110
     *
111
     * If a file object has already been created, it can be passed here.
112
     * If it is left NULL, it will be created when accessed.
113
     *
114
     * @param string                      $path The path to the file being added.
115
     * @param \PHP_CodeSniffer\Files\File $file The file being added.
116
     *
117
     * @return void
118
     */
119
    public function addFile($path, $file=null)
×
120
    {
121
        // No filtering is done for STDIN when the filename
122
        // has not been specified.
123
        if ($path === 'STDIN') {
×
124
            $this->files[$path] = $file;
×
125
            $this->numFiles++;
×
126
            return;
×
127
        }
128

129
        $filterClass = $this->getFilterClass();
×
130

131
        $di       = new RecursiveArrayIterator([$path]);
×
132
        $filter   = new $filterClass($di, $path, $this->config, $this->ruleset);
×
133
        $iterator = new RecursiveIteratorIterator($filter);
×
134

135
        foreach ($iterator as $path) {
×
136
            $this->files[$path] = $file;
×
137
            $this->numFiles++;
×
138
        }
139

140
    }//end addFile()
141

142

143
    /**
144
     * Get the class name of the filter being used for the run.
145
     *
146
     * @return string
147
     * @throws \PHP_CodeSniffer\Exceptions\DeepExitException If the specified filter could not be found.
148
     */
149
    private function getFilterClass()
×
150
    {
151
        $filterType = $this->config->filter;
×
152

153
        if ($filterType === null) {
×
154
            $filterClass = '\PHP_CodeSniffer\Filters\Filter';
×
155
        } else {
156
            if (strpos($filterType, '.') !== false) {
×
157
                // This is a path to a custom filter class.
158
                $filename = realpath($filterType);
×
159
                if ($filename === false) {
×
160
                    $error = "ERROR: Custom filter \"$filterType\" not found".PHP_EOL;
×
161
                    throw new DeepExitException($error, ExitCode::PROCESS_ERROR);
×
162
                }
163

164
                $filterClass = Autoload::loadFile($filename);
×
165
            } else {
166
                $filterClass = '\PHP_CodeSniffer\Filters\\'.$filterType;
×
167
            }
168
        }
169

170
        return $filterClass;
×
171

172
    }//end getFilterClass()
173

174

175
    /**
176
     * Rewind the iterator to the first file.
177
     *
178
     * @return void
179
     */
180
    #[ReturnTypeWillChange]
181
    public function rewind()
182
    {
183
        reset($this->files);
×
184

185
    }//end rewind()
186

187

188
    /**
189
     * Get the file that is currently being processed.
190
     *
191
     * @return \PHP_CodeSniffer\Files\File
192
     */
193
    #[ReturnTypeWillChange]
194
    public function current()
195
    {
196
        $path = key($this->files);
×
197
        if (isset($this->files[$path]) === false) {
×
198
            $this->files[$path] = new LocalFile($path, $this->ruleset, $this->config);
×
199
        }
200

201
        return $this->files[$path];
×
202

203
    }//end current()
204

205

206
    /**
207
     * Return the file path of the current file being processed.
208
     *
209
     * @return string|null Path name or `null` when the end of the iterator has been reached.
210
     */
211
    #[ReturnTypeWillChange]
212
    public function key()
213
    {
214
        return key($this->files);
×
215

216
    }//end key()
217

218

219
    /**
220
     * Move forward to the next file.
221
     *
222
     * @return void
223
     */
224
    #[ReturnTypeWillChange]
225
    public function next()
226
    {
227
        next($this->files);
×
228

229
    }//end next()
230

231

232
    /**
233
     * Checks if current position is valid.
234
     *
235
     * @return boolean
236
     */
237
    #[ReturnTypeWillChange]
238
    public function valid()
239
    {
240
        if (current($this->files) === false) {
×
241
            return false;
×
242
        }
243

244
        return true;
×
245

246
    }//end valid()
247

248

249
    /**
250
     * Return the number of files in the list.
251
     *
252
     * @return integer
253
     */
254
    #[ReturnTypeWillChange]
255
    public function count()
256
    {
257
        return $this->numFiles;
×
258

259
    }//end count()
260

261

262
}//end class
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc