Core: Getter for upper cased identifier must follow unusual naming convention

Created on 19 Jul 2019  路  5Comments  路  Source: api-platform/core

I have a class for which the identifier contains upper case letters:

// ./src/Entity/UDemandeur.php

namespace App\Entity;

use ApiPlatform\Core\Annotation\ApiProperty;
use ApiPlatform\Core\Annotation\ApiResource;
use Doctrine\ORM\Mapping as ORM;

/**
 * @ApiResource()
 * @ORM\Entity(repositoryClass="App\Repository\UDemandeurRepository")
 * @ORM\Table(name="U_DEMANDEUR")
 */
class UDemandeur {
    /**
     * @ApiProperty(identifier=true)
     * @ORM\Id()
     * @ORM\Column(type="string", name="U_DEMANDEURID", unique=true, length=255)
     */
    private $uDemandeurId;

    public function getUDemandeurId(): ?string
    {
        return $this->uDemandeurId;
    }
}

This returns a 404 error:

Not found, because of an invalid identifier configuration

After trying many different naming styles for both the uDemandeurId property and the getUDemandeurId() method, it appears that I have to either rename my property UDemandeurId (but our naming convention requires us to begin property names with a lowercase letter), or to rename my method getuDemandeurId() (but our naming convention requires us to use an uppercase letter after "get").

This is quite singular as the method name getId() works just fine for the property name id, and getUdemandeurid() works for udemandeurid. It seems that having uppercase letters after the first letter of the property names forces the getter to match its case exactly rather than have the usual uppercase letter after "get".

Edit: forgot to specify, PHP 7.2.3, Symfony 4.3.2.

question

All 5 comments

Small update: it looks like the issue arises when the property name starts with two upper case letters:
getUDemandeurId() leads to the PropertyNameCollection to contain 0 => "UDemandeurId" (instead of 0 => "uDemandeurId")
getUdemandeurId() leads to the PropertyNameCollection to contain 0 => "udemandeurId".

I don't understand why changing the case of the second letter also changes the case of the first letter...

This seems to be the intended behavior: in the getters/setters, first letter is made lowercase when getting the parameter name, except if the first two letters are both uppercase.
Good practice then seems to be to have the first letter (after get/set) remain lowercase (e.g. getuDemandeurId for parameter uDemandeurId instead of getUDemandeurId).

Not an api-platform issue after all.

Good practice then seems to be to have the first letter (after get/set) remain lowercase (e.g. getuDemandeurId for parameter uDemandeurId instead of getUDemandeurId).

That is not a good practice. I think it's better to avoid naming properties like that in the first place.

Anyway, the behaviour seems buggy to me. But yeah, it's not an API Platform issue. The problem is in the PropertyInfo component, so you could raise this issue in Symfony.

It seemed buggy to me, but for example in the JavaBean specs (that don't have much to do here but it's an example):

8.8 Capitalization of inferred names.
When we use design patterns to infer a property or event name, we need to decide what rules to follow for capitalizing the inferred name. If we extract the name from the middle of a normal mixedCase style Java name then the name will, by default, begin with a capital letter.
Java programmers are accustomed to having normal identifiers start with lower case letters. Vigorous reviewer input has convinced us that we should follow this same conventional rule for property and event names. Thus when we extract a property or event name from the middle of an existing Java name, we normally convert the first character to lower case. However to support the occasional use of all upper-case names, we check if the first two characters of the name are both upper case and if
so leave it alone.

I'll raise the issue in Symfony, but it looks like it's intended behavior.

Oh, interesting! :smiley:

Was this page helpful?
0 / 5 - 0 ratings