comparison vendor/psy/psysh/test/CodeCleaner/ValidClassNamePassTest.php @ 13:5fb285c0d0e3

Update Drupal core to 8.4.7 via Composer. Security update; I *think* we've been lucky to get away with this so far, as we don't support self-registration which seems to be used by the so-called "drupalgeddon 2" attack that 8.4.5 was vulnerable to.
author Chris Cannam
date Mon, 23 Apr 2018 09:33:26 +0100
parents
children c2387f117808
comparison
equal deleted inserted replaced
12:7a779792577d 13:5fb285c0d0e3
1 <?php
2
3 /*
4 * This file is part of Psy Shell.
5 *
6 * (c) 2012-2018 Justin Hileman
7 *
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
10 */
11
12 namespace Psy\Test\CodeCleaner;
13
14 use Psy\CodeCleaner\ValidClassNamePass;
15
16 class ValidClassNamePassTest extends CodeCleanerTestCase
17 {
18 public function setUp()
19 {
20 $this->setPass(new ValidClassNamePass());
21 }
22
23 /**
24 * @dataProvider getInvalid
25 * @expectedException \Psy\Exception\FatalErrorException
26 */
27 public function testProcessInvalid($code)
28 {
29 $this->parseAndTraverse($code);
30 }
31
32 public function getInvalid()
33 {
34 // class declarations
35 return [
36 // core class
37 ['class stdClass {}'],
38 // capitalization
39 ['class stdClass {}'],
40
41 // collisions with interfaces and traits
42 ['interface stdClass {}'],
43 ['trait stdClass {}'],
44
45 // collisions inside the same code snippet
46 ['
47 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
48 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
49 '],
50 ['
51 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
52 trait Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
53 '],
54 ['
55 trait Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
56 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
57 '],
58 ['
59 trait Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
60 interface Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
61 '],
62 ['
63 interface Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
64 trait Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
65 '],
66 ['
67 interface Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
68 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
69 '],
70 ['
71 class Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
72 interface Psy_Test_CodeCleaner_ValidClassNamePass_Alpha {}
73 '],
74
75 // namespaced collisions
76 ['
77 namespace Psy\\Test\\CodeCleaner {
78 class ValidClassNamePassTest {}
79 }
80 '],
81 ['
82 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
83 class Beta {}
84 }
85 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
86 class Beta {}
87 }
88 '],
89
90 // extends and implements
91 ['class ValidClassNamePassTest extends NotAClass {}'],
92 ['class ValidClassNamePassTest extends ArrayAccess {}'],
93 ['class ValidClassNamePassTest implements stdClass {}'],
94 ['class ValidClassNamePassTest implements ArrayAccess, stdClass {}'],
95 ['interface ValidClassNamePassTest extends stdClass {}'],
96 ['interface ValidClassNamePassTest extends ArrayAccess, stdClass {}'],
97
98 // class instantiations
99 ['new Psy_Test_CodeCleaner_ValidClassNamePass_Gamma();'],
100 ['
101 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
102 new Psy_Test_CodeCleaner_ValidClassNamePass_Delta();
103 }
104 '],
105
106 // class constant fetch
107 ['Psy\\Test\\CodeCleaner\\ValidClassNamePass\\NotAClass::FOO'],
108
109 // static call
110 ['Psy\\Test\\CodeCleaner\\ValidClassNamePass\\NotAClass::foo()'],
111 ['Psy\\Test\\CodeCleaner\\ValidClassNamePass\\NotAClass::$foo()'],
112 ];
113 }
114
115 /**
116 * @dataProvider getValid
117 */
118 public function testProcessValid($code)
119 {
120 $this->parseAndTraverse($code);
121 $this->assertTrue(true);
122 }
123
124 public function getValid()
125 {
126 $valid = [
127 // class declarations
128 ['class Psy_Test_CodeCleaner_ValidClassNamePass_Epsilon {}'],
129 ['namespace Psy\Test\CodeCleaner\ValidClassNamePass; class Zeta {}'],
130 ['
131 namespace { class Psy_Test_CodeCleaner_ValidClassNamePass_Eta {}; }
132 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
133 class Psy_Test_CodeCleaner_ValidClassNamePass_Eta {}
134 }
135 '],
136 ['namespace Psy\Test\CodeCleaner\ValidClassNamePass { class stdClass {} }'],
137
138 // class instantiations
139 ['new stdClass();'],
140 ['new stdClass();'],
141 ['
142 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
143 class Theta {}
144 }
145 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
146 new Theta();
147 }
148 '],
149 ['
150 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
151 class Iota {}
152 new Iota();
153 }
154 '],
155 ['
156 namespace Psy\\Test\\CodeCleaner\\ValidClassNamePass {
157 class Kappa {}
158 }
159 namespace {
160 new \\Psy\\Test\\CodeCleaner\\ValidClassNamePass\\Kappa();
161 }
162 '],
163
164 // Class constant fetch (ValidConstantPassTest validates the actual constant)
165 ['class A {} A::FOO'],
166 ['$a = new DateTime; $a::ATOM'],
167 ['interface A { const B = 1; } A::B'],
168
169 // static call
170 ['DateTime::createFromFormat()'],
171 ['DateTime::$someMethod()'],
172 ['Psy\Test\CodeCleaner\Fixtures\ClassWithStatic::doStuff()'],
173 ['Psy\Test\CodeCleaner\Fixtures\ClassWithCallStatic::doStuff()'],
174
175 // Allow `self` and `static` as class names.
176 ['
177 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
178 public static function getInstance() {
179 return new self();
180 }
181 }
182 '],
183 ['
184 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
185 public static function getInstance() {
186 return new SELF();
187 }
188 }
189 '],
190 ['
191 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
192 public static function getInstance() {
193 return new self;
194 }
195 }
196 '],
197 ['
198 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
199 public static function getInstance() {
200 return new static();
201 }
202 }
203 '],
204 ['
205 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
206 public static function getInstance() {
207 return new Static();
208 }
209 }
210 '],
211 ['
212 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
213 public static function getInstance() {
214 return new static;
215 }
216 }
217 '],
218 ['
219 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
220 public static function foo() {
221 return parent::bar();
222 }
223 }
224 '],
225 ['
226 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
227 public static function foo() {
228 return self::bar();
229 }
230 }
231 '],
232 ['
233 class Psy_Test_CodeCleaner_ValidClassNamePass_ClassWithStatic {
234 public static function foo() {
235 return static::bar();
236 }
237 }
238 '],
239
240 ['class A { static function b() { return new A; } }'],
241 ['
242 class A {
243 const B = 123;
244 function c() {
245 return A::B;
246 }
247 }
248 '],
249 ['class A {} class B { function c() { return new A; } }'],
250
251 // recursion
252 ['class A { function a() { A::a(); } }'],
253
254 // conditionally defined classes
255 ['
256 class A {}
257 if (false) {
258 class A {}
259 }
260 '],
261 ['
262 class A {}
263 if (true) {
264 class A {}
265 } else if (false) {
266 class A {}
267 } else {
268 class A {}
269 }
270 '],
271 // ewww
272 ['
273 class A {}
274 if (true):
275 class A {}
276 elseif (false):
277 class A {}
278 else:
279 class A {}
280 endif;
281 '],
282 ['
283 class A {}
284 while (false) { class A {} }
285 '],
286 ['
287 class A {}
288 do { class A {} } while (false);
289 '],
290 ['
291 class A {}
292 switch (1) {
293 case 0:
294 class A {}
295 break;
296 case 1:
297 class A {}
298 break;
299 case 2:
300 class A {}
301 break;
302 }
303 '],
304 ];
305
306 // Ugh. There's gotta be a better way to test for this.
307 if (class_exists('PhpParser\ParserFactory')) {
308 // PHP 7.0 anonymous classes, only supported by PHP Parser v2.x
309 $valid[] = ['$obj = new class() {}'];
310 }
311
312 if (version_compare(PHP_VERSION, '5.5', '>=')) {
313 $valid[] = ['interface A {} A::class'];
314 $valid[] = ['interface A {} A::CLASS'];
315 $valid[] = ['class A {} A::class'];
316 $valid[] = ['class A {} A::CLASS'];
317 $valid[] = ['A::class'];
318 $valid[] = ['A::CLASS'];
319 }
320
321 return $valid;
322 }
323 }