Issues (363)

src/Converter/PhpSpyCompatibleParser.php (3 issues)

1
<?php
2
3
/**
4
 * This file is part of the reliforp/reli-prof package.
5
 *
6
 * (c) sji <[email protected]>
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
declare(strict_types=1);
13
14
namespace Reli\Converter;
15
16
use PhpCast\Cast;
0 ignored issues
show
The type PhpCast\Cast was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
17
18
final class PhpSpyCompatibleParser
19
{
20
    /**
21
     * @param resource $fp
22
     * @return iterable<ParsedCallTrace>
23
     */
24
    public function parseFile($fp): iterable
25
    {
26
        $buffer = [];
27
        $lineno_before_parse = 0;
28
        while (($line = fgets($fp)) !== false) {
29
            $lineno_before_parse++;
30
            $line = trim($line);
31
            if ($line !== '') {
32
                $buffer[] = [$line, $lineno_before_parse];
33
                continue;
34
            }
35
            yield $this->parsePhpSpyCompatible($buffer);
36
            $buffer = [];
37
        }
38
    }
39
40
    /** @param array{string, int}[] $buffer */
0 ignored issues
show
Documentation Bug introduced by
The doc comment array{string, int}[] at position 2 could not be parsed: Expected ':' at position 2, but found 'string'.
Loading history...
41
    private function parsePhpSpyCompatible(array $buffer): ParsedCallTrace
42
    {
43
        $frames = [];
44
        foreach ($buffer as [$line_buffer, $lineno_before_parse]) {
45
            $result = explode(' ', $line_buffer);
46
            [$depth, $name, $file_line] = $result;
47
            if ($depth === '#') { // comment
48
                continue;
49
            }
50
            [$file, $line] = $this->splitLineNumberAndFilePath($file_line, $lineno_before_parse);
51
            $frames[] = new ParsedCallFrame(
52
                $name,
53
                $file,
54
                $line,
55
                new PhpSpyCompatibleDataContext($lineno_before_parse),
56
            );
57
        }
58
        return new ParsedCallTrace(...$frames);
59
    }
60
61
    /**
62
     * @param string $file_line
63
     * @return array{non-empty-string, int}
0 ignored issues
show
Documentation Bug introduced by
The doc comment array{non-empty-string, int} at position 2 could not be parsed: Expected ':' at position 2, but found 'non-empty-string'.
Loading history...
64
     */
65
    private function splitLineNumberAndFilePath(string $file_line, int $lineno_before_parse): array
66
    {
67
        if ($file_line === '') {
68
            throw new PhpSpyCompatibleParserException(
69
                'missing line number and file path at line' . $lineno_before_parse,
70
                $lineno_before_parse,
71
            );
72
        }
73
74
        $separator_position = strrpos($file_line, ':');
75
        if ($separator_position === false) {
76
            throw new PhpSpyCompatibleParserException(
77
                'missing separator ":" between line number and file path at line ' . $lineno_before_parse,
78
                $lineno_before_parse,
79
            );
80
        }
81
        $line = substr($file_line, $separator_position + 1);
82
        $file = substr($file_line, 0, $separator_position);
83
        if ($file === '') {
84
            throw new PhpSpyCompatibleParserException(
85
                'missing file path at line ' . $lineno_before_parse,
86
                $lineno_before_parse,
87
            );
88
        }
89
        return [$file, Cast::toInt($line)];
90
    }
91
}
92