Skip to content

Commit 97212fd

Browse files
committed
Add some more helpers
1 parent c7dcbd6 commit 97212fd

File tree

1 file changed

+164
-1
lines changed

1 file changed

+164
-1
lines changed

Inpsyde/Helpers.php

Lines changed: 164 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -129,4 +129,167 @@ public static function tokenName(File $file, int $position): string
129129

130130
return $file->getTokens()[$namePosition]['content'];
131131
}
132-
}
132+
133+
/**
134+
* @param int $start
135+
* @param int $end
136+
* @param File $file
137+
* @param array ...$types
138+
* @return array[]
139+
*/
140+
public static function filterTokensByType(
141+
int $start,
142+
int $end,
143+
File $file,
144+
...$types
145+
): array {
146+
147+
return array_filter(
148+
$file->getTokens(),
149+
function (array $token, int $position) use ($start, $end, $types): bool {
150+
return
151+
$position >= $start
152+
&& $position <= $end
153+
&& in_array($token['code'] ?? '', $types, true);
154+
},
155+
ARRAY_FILTER_USE_BOTH
156+
);
157+
}
158+
159+
/**
160+
* @param File $file
161+
* @param int $closurePosition
162+
* @param bool $lookForFilters
163+
* @param bool $lookForActions
164+
* @return bool
165+
*/
166+
public static function isHookClosure(
167+
File $file,
168+
int $closurePosition,
169+
bool $lookForFilters = true,
170+
bool $lookForActions = true
171+
): bool {
172+
173+
$tokens = $file->getTokens();
174+
if (($tokens[$closurePosition]['code'] ?? '') !== T_CLOSURE) {
175+
return false;
176+
}
177+
178+
$lookForComma = $file->findPrevious(
179+
[T_WHITESPACE],
180+
$closurePosition - 1,
181+
null,
182+
true,
183+
null,
184+
true
185+
);
186+
187+
if (!$lookForComma || ($tokens[$lookForComma]['code'] ?? '') !== T_COMMA) {
188+
return false;
189+
}
190+
191+
$functionCallOpen = $file->findPrevious(
192+
[T_OPEN_PARENTHESIS],
193+
$lookForComma - 2,
194+
null,
195+
false,
196+
null,
197+
true
198+
);
199+
200+
if (!$functionCallOpen) {
201+
return false;
202+
}
203+
204+
$functionCall = $file->findPrevious(
205+
[T_WHITESPACE],
206+
$functionCallOpen - 1,
207+
null,
208+
true,
209+
null,
210+
true
211+
);
212+
213+
$actions = [];
214+
$lookForFilters and $actions[] = 'add_filter';
215+
$lookForActions and $actions[] = 'add_action';
216+
217+
return in_array(($tokens[$functionCall]['content'] ?? ''), $actions, true);
218+
}
219+
220+
/**
221+
* @param File $file
222+
* @param int $functionPosition
223+
* @return array
224+
*/
225+
public static function functionBoundaries(File $file, int $functionPosition): array
226+
{
227+
$tokens = $file->getTokens();
228+
$functionStart = $tokens[$functionPosition]['scope_opener'] ?? 0;
229+
$functionEnd = $tokens[$functionPosition]['scope_closer'] ?? 0;
230+
if (!$functionStart || !$functionEnd || $functionStart >= ($functionEnd - 1)) {
231+
return [-1, -1];
232+
}
233+
234+
return [$functionStart, $functionEnd];
235+
}
236+
237+
/**
238+
* @param File $file
239+
* @param int $functionPosition
240+
* @return array
241+
*/
242+
public static function countReturns(File $file, int $functionPosition): array
243+
{
244+
list($functionStart, $functionEnd) = self::functionBoundaries($file, $functionPosition);
245+
if ($functionStart < 0 || $functionEnd <= 0) {
246+
return [0, 0];
247+
}
248+
249+
$returnTokens = self::filterTokensByType(
250+
$functionStart,
251+
$functionEnd,
252+
$file,
253+
T_RETURN
254+
);
255+
256+
if (!$returnTokens) {
257+
return [0, 0];
258+
}
259+
260+
$nonVoidReturnCount = $voidReturnCount = 0;
261+
$scopeClosers = [];
262+
foreach ($returnTokens as $i => $token) {
263+
if ($scopeClosers && $i === $scopeClosers[0]) {
264+
array_shift($scopeClosers);
265+
}
266+
if ($token['type'] === 'T_FUNCTION') {
267+
array_unshift($scopeClosers, $token['scope_closer']);
268+
}
269+
if (!$scopeClosers) {
270+
Helpers::isVoidReturn($file, $i) ? $voidReturnCount++ : $nonVoidReturnCount++;
271+
}
272+
}
273+
274+
return [$nonVoidReturnCount, $voidReturnCount];
275+
}
276+
277+
/**
278+
* @param File $file
279+
* @param int $returnPosition
280+
* @return bool
281+
*/
282+
public static function isVoidReturn(File $file, int $returnPosition): bool
283+
{
284+
$tokens = $file->getTokens();
285+
286+
if (($tokens[$returnPosition]['code'] ?? '') !== T_RETURN) {
287+
return false;
288+
}
289+
290+
$returnPosition++;
291+
$nextToReturn = $file->findNext([T_WHITESPACE], $returnPosition, null, true, null, true);
292+
293+
return $nextToReturn && ($tokens[$nextToReturn]['type'] ?? '') === 'T_SEMICOLON';
294+
}
295+
}

0 commit comments

Comments
 (0)