# RFC: Casing of acronyms in class and method names

- Status: Accepted
- Authors: Tim Düsterhus, timwolla@php.net
- Date: 2024-04-05
- Version: 1.0
- Implementation: https://github.com/php/php-src/pull/14169, https://github.com/php/policies/pull/7
- Original: https://wiki.php.net/rfc/class-naming-acronyms
- Page: https://externals.io/rfc/class-naming-acronyms
- More for agents: search with https://externals.io/search.md?q={query} · RFCs at https://externals.io/rfc.md · JSON API at https://externals.io/api · documentation at https://externals.io/llms.txt

## Votes

### Adopt the updated class naming policy and adjust the new names introduced in PHP 8.4? (closed)

yes: 23 · no: 1

Voters: alcaeus (yes), beberlei (yes), crell (yes), devnexen (yes), dharman (yes), ericmann (no), galvao (yes), girgias (yes), ilutov (yes), kguest (yes), klaussilveira (yes), kocsismate (yes), mauricio (yes), mbeccati (yes), nicolasgrekas (yes), nielsdos (yes), ocramius (yes), petk (yes), ramsey (yes), saki (yes), sergey (yes), theodorejb (yes), thorstenr (yes), timwolla (yes)

## Discussions on the mailing list

- [Casing of acronyms in class and method names](https://externals.io/message/120959.md) — started on 2023-08-30, 8 messages
- [\[RFC\] Casing of acronyms in class and method names](https://externals.io/message/122975.md) — started on 2024-04-05, 24 messages
- [PDO subclass names](https://externals.io/message/123166.md) — started on 2024-04-21, 13 messages
- [\[VOTE\] Casing of acronyms in class and method names](https://externals.io/message/123167.md) — started on 2024-04-22, 2 messages

---

## Introduction

The results of the [Class Naming RFC](https://externals.io/rfc/class-naming) decided that class names should be written in PascalCase (“Upper Camel Case”), with the exception of acronyms, which should be included in UPPERCASE. This RFC proposes to revisit the prior decision, instead treating acronyms like regular words, making classnames consistent PascalCase.

### Reasoning

#### It is not consistently applied

As an example ext/json has `JsonException` which should've been `JSONException` according to the previous RFC’s results. In fact [JsonException’s RFC](https://externals.io/rfc/json_throw_on_error) was created just 3 months (!) after the class naming RFC in September 2017.

Another example is ext/curl which has both `CurlHandle` and `CURLFile`. `CURLFile` predates the RFC, but there's also `CURLStringFile` which was added in PHP 8.1 and likely followed `CURLFile`’s naming for consistency, but violating the RFC and being inconsistent with `CurlHandle`.

ext/random’s `Random\Engine\PcgOneseq128XslRr64` would've needed to be called `Random\Engine\PCGOneseq128XSLRR64` according to the class naming RFC.

The [PDO driver specific sub-classes](https://externals.io/rfc/pdo_driver_specific_subclasses) RFC voted (and accepted) for PHP 8.3 and implemented in PHP 8.4 uses Pdo&lt;Driver&gt;, e.g. PdoOdbc instead of PDOODBC.

#### It decreases readability

It is well-established in accessibility circles that ALL CAPS text is harder to read than Mixed Case, as mixed case provides greater vertical variation between letters, making it easier to read, especially for people with various reading disorders.

Most accessibility organizations recommend against ALL CAPS. For example:

- [W3C](https://w3c.github.io/low-vision-a11y-tf/requirements.html#capitalization)
- [Harvard University](https://accessibility.huit.harvard.edu/design-readability)
- [The A11y Project](https://www.a11yproject.com/posts/how-to-accessible-heading-structure/#all-caps)

That issue is amplified if multiple acronyms follow each other. One example is the `PCGOneseq128XSLRR64` mentioned above: It’s not clear that `XSL` (XorShiftLow) and `RR` (RandomlyRotate) are two different acronyms.

Likewise `PDOODBC` is much harder to parse than `PdoOdbc`.

Another example might be JavaScript’s `XMLHttpRequest` which incidentally mixes both variants. According to the class naming RFC it would need to be called `XMLHTTPRequest`, resulting in 8 consecutive uppercase characters.

#### The userland convention is mostly MixedCase

Although there is no formal standard in userland for handling initialisms, the most widely used convention is to only capitalize the first letter. For example:

- Symfony's HttpFoundation: <https://github.com/symfony/symfony/tree/6.4/src/Symfony/Component/HttpFoundation>
- Symfony's CssSelector: <https://github.com/symfony/symfony/tree/6.4/src/Symfony/Component/CssSelector>
- Laravel's HtmlString: <https://github.com/laravel/framework/blob/10.x/src/Illuminate/Support/HtmlString.php>
- PSR-7: <https://www.php-fig.org/psr/psr-7/>
- PSR-18: <https://www.php-fig.org/psr/psr-18/>
- ramsey/uuid: <https://github.com/ramsey/uuid/tree/4.x/src>
- Flysystem is a little inconsistent, but has 'Ftp': <https://github.com/thephpleague/flysystem/tree/3.x/src/Ftp>
- PHPUnit is a little inconsistent, but has 'Xml' and 'Json': <https://github.com/sebastianbergmann/phpunit/tree/main/src/Util>
- Doctrine is also a little inconsistent, but has 'Dsn' and 'Sql' (but also 'SQL'): <https://github.com/doctrine/dbal/tree/3.9.x/src/Schema/Visitor> and <https://github.com/doctrine/dbal/blob/3.9.x/src/Tools/DsnParser.php>

Although this RFC has no direct impact on userland code, normalizing conventions between Internals and userland has many benefits. The PER-CS working group, part of the PHP-FIG, has been asked to adopt a standard for initialisms and would likely follow suit with this RFC if passed.

## Proposal

### Update to the Policy

The class naming policy should be updated to the following, with changes highlighted:

Method names follow the studlyCaps (also referred to as bumpy case or camel caps) naming convention, with care taken to minimize the letter count. The initial letter of the name is lowercase, and each letter that starts a new word is capitalized.

Class names should be descriptive nouns in PascalCase and as short as possible. Each word in the class name should start with a capital letter, without underscore delimiters. The class name should be prefixed with the name of the “parent set” (e.g. the name of the extension) if no namespaces are used.

Abbreviations and acronyms as well as initialisms should be avoided wherever possible, unless they are much more widely used than the long form (e.g. HTTP or URL). Abbreviations start with a capital letter followed by lowercase letters, whereas acronyms and initialisms are written according to their standard notation. **Abbreviations, acronyms, and initialisms should be treated like regular words, thus they should be written with an uppercase first character, followed by lowercase characters.** Usage of acronyms and initialisms is not allowed if they are not widely adopted and recognized as such.

**Diverging from this policy is allowed to keep internal consistency within a single extension, if the name follows an established, language-agnostic standard, or for other reasons, if those reasons are properly justified and voted on as part of the RFC process.**

#### Examples

Good method names:

```
connect()
getData()
buildSomeWidget()
performHttpRequest()
```

Bad method names:

```
get_Data()
buildsomewidget()
getI()
performHTTPRequest()
```

Good class names:

```
Curl
CurlResponse
HttpStatusCode
Url
BtreeMap // B-tree Map
UserId // User Identifier
Char // Character
Intl // Internationalization
Ssl\Certificate
Ssl\Crl // Certificate Revocation List
Ssl\CrlUrl
```

Bad class names:

```
curl
curl_response
HTTPStatusCode
URL
BTreeMap
UserID // User Identifier
CHAR
INTL
SSL\Certificate
SSL\CRL
SSL\CRLURL
```

### Adjusting class &amp; method names added in PHP 8.4

The [DOM HTML5 parsing and serialization RFC](https://externals.io/rfc/domdocument_html5_parser) introduced new class names and method names that violate the updated naming policy, should this RFC be accepted. As part of this RFC, the following changes will be made:

- The `DOM` namespace will be renamed to `Dom`, affecting everything contained within it.
- DOM\\DTDNamedNodeMap -&gt; Dom\\DtdNamedNodeMap
- DOM\\HTMLCollection -&gt; Dom\\HTMLCollection (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the name)
- DOM\\CDATASection -&gt; Dom\\CDATASection (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the name)
- DOM\\HTMLDocument -&gt; Dom\\HTMLDocument (Justification: Consistency with XMLDocument)
- DOM\\XMLDocument -&gt; Dom\\XMLDocument (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the name)
- DOM\\XPath -&gt; Dom\\XPath (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the XPath interfaces that use this casing)
- DOM\\Implementation::createHTMLDocument() -&gt; Dom\\Implementation::createHtmlDocument()
- DOM\\Node::lookupNamespaceURI() -&gt; Dom\\Node::lookupNamespaceURI() (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the name)
- DOM\\\*::\*NS() -&gt; Dom\\\*::\*NS() (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) generally specifies the NS suffix in this casing)
- DOM\\DocumentFragment::appendXML() -&gt; Dom\\DocumentFragment::appendXml()
- DOM\\Document::createCDATASection() -&gt; Dom\\Document::createCDATASection() (Justification: The [DOM Standard](https://dom.spec.whatwg.org/) specifies the name)
- DOM\\Document::relaxNGValidate() -&gt; Dom\\Document::relaxNgValidate()
- DOM\\Document::relaxNGValidateSource() -&gt; Dom\\Document::relaxNgValidateSource()
- DOM\\HTMLDocument::saveXML() -&gt; Dom\\HTMLDocument::saveXml()
- DOM\\HTMLDocument::saveXMLFile() -&gt; Dom\\HTMLDocument::saveXmlFile()
- DOM\\HTMLDocument::saveHTML() -&gt; Dom\\HTMLDocument::saveHtml()
- DOM\\HTMLDocument::saveHTMLFile() -&gt; Dom\\HTMLDocument::saveHtmlFile()
- DOM\\XMLDocument::saveXML() -&gt; Dom\\XMLDocument::saveXml()
- DOM\\XMLDocument::saveXMLFile() -&gt; Dom\\XMLDocument::saveXmlFile()

For the [Improve callbacks in ext/dom and ext/xsl RFC](https://externals.io/rfc/improve_callbacks_dom_and_xsl) the following changes will be made:

- \\DOMXPath::registerPhpFunctionNS() -&gt; \\DOMXPath::registerPhpFunctionNS() (Justification: Consistency with the \*NS() methods in ext/dom)
- \\DOM\\XPath::registerPhpFunctionNS() -&gt; \\Dom\\XPath::registerPhpFunctionNS() (Justification: see above)
- \\XSLTProcessor::registerPHPFunctionNS() -&gt; \\XSLTProcessor::registerPHPFunctionNS() (Justification: Consistency with \\XSLTProcessor::registerPHPFunctions(), which unfortunately is inconsistent with \\DOMXPath).

## Backward Incompatible Changes

Existing class and method names in released versions are not affected, thus there are not backwards incompatible changes. This is a policy RFC.

## Proposed PHP Version(s)

Next PHP 8.x (PHP 8.4).

## RFC Impact

### To SAPIs

SAPIs that expose classes should take the RFC results into account.

### To Existing Extensions

Extensions should take the RFC results into account.

### To Opcache

None.

### New Constants

None.

### php.ini Defaults

None.

## Open Issues

None.

## Unaffected PHP Functionality

Everything that is not a class name of an internal class. Everything that is already in PHP.

## Future Scope

None.

## Proposed Voting Choices

**Vote: Adopt the updated class naming policy and adjust the new names introduced in PHP 8.4?** — yes: 23 · no: 1 (closed)

## Patches and Tests

None, yet. This RFC will result in changes to:

- [https://github.com/php/php-src/blob/536305436f44e91731bc5c86e06f137e44a01109/CODING\_STANDARDS.md#L173-L211](https://github.com/php/php-src/blob/536305436f44e91731bc5c86e06f137e44a01109/CODING_STANDARDS.md#L173-L211)
- <https://github.com/php/policies/blob/main/coding-standards-and-naming.rst>

## Implementation

- <https://github.com/php/php-src/pull/14169>
- <https://github.com/php/policies/pull/7>

## References

- [Class Naming RFC](https://externals.io/rfc/class-naming)
- Prior mailing list discussion: <https://externals.io/message/120959#120959>
- Discussion in PHP-FIG for PER-CS: <https://github.com/php-fig/per-coding-style/issues/83>

## Rejected Features

n/a
