Skip to content

Commit

Permalink
Enhancement: Document array shapes
Browse files Browse the repository at this point in the history
  • Loading branch information
localheinz committed Mar 19, 2023
1 parent e9e9b31 commit c9b9ab7
Show file tree
Hide file tree
Showing 15 changed files with 391 additions and 49 deletions.
56 changes: 42 additions & 14 deletions .psalm/baseline.xml
Expand Up @@ -10,17 +10,28 @@
</RedundantCondition>
</file>
<file src="src/Data/ProcessedCodeCoverageData.php">
<InvalidArgument>
<code>$functionData</code>
<code>$functionData</code>
</InvalidArgument>
<PossiblyNullArgument>
<code><![CDATA[$this->functionCoverage[$file][$functionName]['branches'][$branchId]['hit']]]></code>
<code><![CDATA[$newData->lineCoverage[$file][$line]]]></code>
</PossiblyNullArgument>
<PossiblyNullArrayAccess>
<code><![CDATA[$this->functionCoverage[$file][$functionName]['branches']]]></code>
<code><![CDATA[$this->functionCoverage[$file][$functionName]['branches'][$branchId]]]></code>
<code><![CDATA[$this->functionCoverage[$file][$functionName]['branches'][$branchId]['hit']]]></code>
</PossiblyNullArrayAccess>
<PossiblyNullArrayAssignment>
<code><![CDATA[$this->functionCoverage[$file][$functionName]['branches']]]></code>
</PossiblyNullArrayAssignment>
<PropertyTypeCoercion>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->functionCoverage]]></code>
<code><![CDATA[$this->lineCoverage]]></code>
<code><![CDATA[$this->lineCoverage]]></code>
<code><![CDATA[$this->lineCoverage]]></code>
</PropertyTypeCoercion>
</file>
<file src="src/Driver/PcovDriver.php">
<UndefinedConstant>
Expand Down Expand Up @@ -67,11 +78,28 @@
</UnsupportedReferenceUsage>
</file>
<file src="src/Node/File.php">
<InvalidPropertyAssignmentValue>
<code><![CDATA[$this->codeUnitsByLine]]></code>
<code><![CDATA[$this->codeUnitsByLine]]></code>
<code><![CDATA[$this->codeUnitsByLine]]></code>
</InvalidPropertyAssignmentValue>
<PropertyTypeCoercion>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->classes]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
<code><![CDATA[$this->traits]]></code>
</PropertyTypeCoercion>
</file>
<file src="src/Node/Iterator.php">
<ArgumentTypeCoercion>
Expand Down
11 changes: 8 additions & 3 deletions src/CodeCoverage.php
Expand Up @@ -35,6 +35,11 @@

/**
* Provides collection functionality for PHP code coverage information.
*
* @psalm-type TestType = array{
* size: string,
* status: string,
* }
*/
final class CodeCoverage
{
Expand All @@ -51,7 +56,7 @@ final class CodeCoverage
private bool $useAnnotationsForIgnoringCode = true;

/**
* @psalm-var array<string, array{size: string, status: string}>
* @psalm-var array<string, TestType>
*/
private array $tests = [];

Expand Down Expand Up @@ -120,15 +125,15 @@ public function setData(ProcessedCodeCoverageData $data): void
}

/**
* @psalm-return array<string, array{size: string, status: string}>
* @psalm-return array<string, TestType>
*/
public function getTests(): array
{
return $this->tests;
}

/**
* @psalm-param array<string, array{size: string, status: string}> $tests
* @psalm-param array<string, TestType> $tests
*/
public function setTests(array $tests): void
{
Expand Down
28 changes: 28 additions & 0 deletions src/Data/ProcessedCodeCoverageData.php
Expand Up @@ -20,19 +20,43 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @psalm-import-type XdebugFunctionCoverageType from \SebastianBergmann\CodeCoverage\Driver\XdebugDriver
* @psalm-import-type XdebugFunctionsCoverageType from \SebastianBergmann\CodeCoverage\Driver\XdebugDriver
*
* @psalm-type TestIdType = string
*/
final class ProcessedCodeCoverageData
{
/**
* Line coverage data.
* An array of filenames, each having an array of linenumbers, each executable line having an array of testcase ids.
*
* @psalm-var array<string, array<int, null|list<TestIdType>>>
*/
private array $lineCoverage = [];

/**
* Function coverage data.
* Maintains base format of raw data (@see https://xdebug.org/docs/code_coverage), but each 'hit' entry is an array
* of testcase ids.
*
* @psalm-var array<string, array<string, array{
* branches: array<int, array{
* op_start: int,
* op_end: int,
* line_start: int,
* line_end: int,
* hit: list<TestIdType>,
* out: array<int, int>,
* out_hit: array<int, int>,
* }>,
* paths: array<int, array{
* path: array<int, int>,
* hit: list<TestIdType>,
* }>,
* hit: list<TestIdType>
* }>>
*/
private array $functionCoverage = [];

Expand Down Expand Up @@ -213,6 +237,8 @@ private function priorityForLine(array $data, int $line): int

/**
* For a function we have never seen before, copy all data over and simply init the 'hit' array.
*
* @psalm-param XdebugFunctionCoverageType $functionData
*/
private function initPreviouslyUnseenFunction(string $file, string $functionName, array $functionData): void
{
Expand All @@ -231,6 +257,8 @@ private function initPreviouslyUnseenFunction(string $file, string $functionName
* For a function we have seen before, only copy over and init the 'hit' array for any unseen branches and paths.
* Techniques such as mocking and where the contents of a file are different vary during tests (e.g. compiling
* containers) mean that the functions inside a file cannot be relied upon to be static.
*
* @psalm-param XdebugFunctionCoverageType $functionData
*/
private function initPreviouslySeenFunction(string $file, string $functionName, array $functionData): void
{
Expand Down
24 changes: 22 additions & 2 deletions src/Data/RawCodeCoverageData.php
Expand Up @@ -26,6 +26,10 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @psalm-import-type XdebugFunctionsCoverageType from \SebastianBergmann\CodeCoverage\Driver\XdebugDriver
* @psalm-import-type XdebugCodeCoverageWithoutPathCoverageType from \SebastianBergmann\CodeCoverage\Driver\XdebugDriver
* @psalm-import-type XdebugCodeCoverageWithPathCoverageType from \SebastianBergmann\CodeCoverage\Driver\XdebugDriver
*/
final class RawCodeCoverageData
{
Expand All @@ -35,20 +39,26 @@ final class RawCodeCoverageData
private static array $emptyLineCache = [];

/**
* @see https://xdebug.org/docs/code_coverage for format
* @psalm-var XdebugCodeCoverageWithoutPathCoverageType
*/
private array $lineCoverage;

/**
* @see https://xdebug.org/docs/code_coverage for format
* @psalm-var array<string, XdebugFunctionsCoverageType>
*/
private array $functionCoverage;

/**
* @psalm-param XdebugCodeCoverageWithoutPathCoverageType $rawCoverage
*/
public static function fromXdebugWithoutPathCoverage(array $rawCoverage): self
{
return new self($rawCoverage, []);
}

/**
* @psalm-param XdebugCodeCoverageWithPathCoverageType $rawCoverage
*/
public static function fromXdebugWithPathCoverage(array $rawCoverage): self
{
$lineCoverage = [];
Expand All @@ -73,6 +83,10 @@ public static function fromUncoveredFile(string $filename, FileAnalyser $analyse
return new self([$filename => $lineCoverage], []);
}

/**
* @psalm-param XdebugCodeCoverageWithoutPathCoverageType $lineCoverage
* @psalm-param array<string, XdebugFunctionsCoverageType> $functionCoverage
*/
private function __construct(array $lineCoverage, array $functionCoverage)
{
$this->lineCoverage = $lineCoverage;
Expand All @@ -86,11 +100,17 @@ public function clear(): void
$this->lineCoverage = $this->functionCoverage = [];
}

/**
* @psalm-return XdebugCodeCoverageWithoutPathCoverageType
*/
public function lineCoverage(): array
{
return $this->lineCoverage;
}

/**
* @psalm-return array<string, XdebugFunctionsCoverageType>
*/
public function functionCoverage(): array
{
return $this->functionCoverage;
Expand Down
30 changes: 30 additions & 0 deletions src/Driver/XdebugDriver.php
Expand Up @@ -31,6 +31,34 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @see https://xdebug.org/docs/code_coverage#xdebug_get_code_coverage
*
* @psalm-type XdebugLinesCoverageType = array<int, int>
* @psalm-type XdebugBranchCoverageType = array{
* op_start: int,
* op_end: int,
* line_start: int,
* line_end: int,
* hit: int,
* out: array<int, int>,
* out_hit: array<int, int>,
* }
* @psalm-type XdebugPathCoverageType = array{
* path: array<int, int>,
* hit: int,
* }
* @psalm-type XdebugFunctionCoverageType = array{
* branches: array<int, XdebugBranchCoverageType>,
* paths: array<int, XdebugPathCoverageType>,
* }
* @psalm-type XdebugFunctionsCoverageType = array<string, XdebugFunctionCoverageType>
* @psalm-type XdebugPathAndBranchesCoverageType = array{
* lines: XdebugLinesCoverageType,
* functions: XdebugFunctionsCoverageType,
* }
* @psalm-type XdebugCodeCoverageWithoutPathCoverageType = array<string, XdebugLinesCoverageType>
* @psalm-type XdebugCodeCoverageWithPathCoverageType = array<string, XdebugPathAndBranchesCoverageType>
*/
final class XdebugDriver extends Driver
{
Expand Down Expand Up @@ -84,9 +112,11 @@ public function stop(): RawCodeCoverageData
xdebug_stop_code_coverage();

if ($this->collectsBranchAndPathCoverage()) {
/* @var XdebugCodeCoverageWithPathCoverageType $data */
return RawCodeCoverageData::fromXdebugWithPathCoverage($data);
}

/* @var XdebugCodeCoverageWithoutPathCoverageType $data */
return RawCodeCoverageData::fromXdebugWithoutPathCoverage($data);
}

Expand Down
16 changes: 15 additions & 1 deletion src/Node/AbstractNode.php
Expand Up @@ -19,6 +19,11 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @psalm-import-type LinesOfCodeType from \SebastianBergmann\CodeCoverage\StaticAnalysis\FileAnalyser
* @psalm-import-type ProcessedFunctionType from \SebastianBergmann\CodeCoverage\Node\File
* @psalm-import-type ProcessedClassType from \SebastianBergmann\CodeCoverage\Node\File
* @psalm-import-type ProcessedTraitType from \SebastianBergmann\CodeCoverage\Node\File
*/
abstract class AbstractNode implements Countable
{
Expand Down Expand Up @@ -163,14 +168,23 @@ public function numberOfTestedFunctionsAndMethods(): int
return $this->numberOfTestedFunctions() + $this->numberOfTestedMethods();
}

/**
* @psalm-return array<string, ProcessedClassType>
*/
abstract public function classes(): array;

/**
* @psalm-return array<string, ProcessedTraitType>
*/
abstract public function traits(): array;

/**
* @psalm-return array<string, ProcessedFunctionType>
*/
abstract public function functions(): array;

/**
* @psalm-return array{linesOfCode: int, commentLinesOfCode: int, nonCommentLinesOfCode: int}
* @psalm-return LinesOfCodeType
*/
abstract public function linesOfCode(): array;

Expand Down
6 changes: 5 additions & 1 deletion src/Node/Builder.php
Expand Up @@ -27,6 +27,8 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @psalm-import-type TestType from \SebastianBergmann\CodeCoverage\CodeCoverage
*/
final class Builder
{
Expand Down Expand Up @@ -56,7 +58,7 @@ public function build(CodeCoverage $coverage): Directory
}

/**
* @psalm-param array<string, array{size: string, status: string}> $tests
* @psalm-param array<string, TestType> $tests
*/
private function addItems(Directory $root, array $items, array $tests): void
{
Expand Down Expand Up @@ -129,6 +131,8 @@ private function addItems(Directory $root, array $items, array $tests): void
* )
* )
* </code>
*
* @psalm-return array<string, array<string, array{lineCoverage: array<int, int>, functionCoverage: array<string, array<int, int>>}>>
*/
private function buildDirectoryStructure(ProcessedCodeCoverageData $data): array
{
Expand Down
10 changes: 8 additions & 2 deletions src/Node/Directory.php
Expand Up @@ -16,6 +16,12 @@

/**
* @internal This class is not covered by the backward compatibility promise for phpunit/php-code-coverage
*
* @psalm-type LinesOfCodeInDirectoryType = array{
* linesOfCode: int,
* commentLinesOfCode: int,
* nonCommentLinesOfCode: int,
* }
*/
final class Directory extends AbstractNode implements IteratorAggregate
{
Expand All @@ -38,7 +44,7 @@ final class Directory extends AbstractNode implements IteratorAggregate
private ?array $functions = null;

/**
* @psalm-var null|array{linesOfCode: int, commentLinesOfCode: int, nonCommentLinesOfCode: int}
* @psalm-var null|LinesOfCodeInDirectoryType
*/
private ?array $linesOfCode = null;
private int $numFiles = -1;
Expand Down Expand Up @@ -161,7 +167,7 @@ public function functions(): array
}

/**
* @psalm-return array{linesOfCode: int, commentLinesOfCode: int, nonCommentLinesOfCode: int}
* @psalm-return LinesOfCodeInDirectoryType
*/
public function linesOfCode(): array
{
Expand Down

0 comments on commit c9b9ab7

Please sign in to comment.