Skip to content

Incorrect statement count in coverage report for constructor property promotion #1014

@thirsch

Description

@thirsch
Q A
php-code-coverage version 10.1.6
PHP version 8.2.8
Driver not relevant
Installation Method Composer
Usage Method PHPUnit
PHPUnit version (if used) 10.3.5

If using constructor property promotion in a single line while defining a new instance of an object, the clover report does not contain a line of type stmt but counts it as a statement in the metrics. On the other hand, every method is mentioned on it's own but I'm not able to distinguish a constructor with an kind of inline statement from a regular method without.

I hope the following two examples make it more clear. I've written both of them as unittests in php-code-coverage, but I'm not sure what the correct solution might be? Should there be a second line for the same num with type stmt? Is that even allowed in the clover format?

Example 1 (single line)

<?php

class CoveredClassWithConstructorPropertyPromotion
{
    public function __construct(private DateTimeInterface $dateTime = new DateTime()) {

    }
}

Generated clover.xml:

<?xml version="1.0" encoding="UTF-8"?>
<coverage generated="%i">
  <project timestamp="%i">
    <file name="%s%esource_with_class_and_constructor_property_promotion.php">
      <class name="CoveredClassWithConstructorPropertyPromotion" namespace="global">
        <metrics complexity="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
      </class>
      <line num="5" type="method" name="__construct" visibility="public" complexity="1" crap="1" count="1"/>
      <line num="8" type="stmt" count="1"/>
      <metrics loc="10" ncloc="10" classes="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
    </file>
    <metrics files="1" loc="10" ncloc="10" classes="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
  </project>
</coverage>

Please note the attributes "statements" and "coveredstatements" both being 2, but only one line of type stmt.

Example 2 (with linebreak)

<?php

class CoveredClassWithConstructorPropertyPromotion
{
    public function __construct(
        private DateTimeInterface $dateTime = new DateTime()
    ) {

    }
}

Generated clover.xml:

<?xml version="1.0" encoding="UTF-8"?>
<coverage generated="%i">
  <project timestamp="%i">
    <file name="%s%esource_with_class_and_constructor_property_promotion.php">
      <class name="CoveredClassWithConstructorPropertyPromotion" namespace="global">
        <metrics complexity="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
      </class>
      <line num="5" type="method" name="__construct" visibility="public" complexity="1" crap="1" count="1"/>
      <line num="6" type="stmt" count="1"/>
      <line num="9" type="stmt" count="1"/>
      <metrics loc="11" ncloc="11" classes="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
    </file>
    <metrics files="1" loc="11" ncloc="11" classes="1" methods="1" coveredmethods="1" conditionals="0" coveredconditionals="0" statements="2" coveredstatements="2" elements="3" coveredelements="3"/>
  </project>
</coverage>

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions