Skip to content

PHP Style Guide

PHP code style and formatting conventions for the RightCapital backend team.

When using studly and camel cases, acronyms (API, SSO) MUST be transformed to the corresponding letter case. Example: “LPL SSO API” → LplSsoApi (studly) or lplSsoApi (camel), NOT LPLSSOAPI.

Namespace, class, interface, trait, enum names

Section titled “Namespace, class, interface, trait, enum names”

MUST be in StudlyCaps.

Trait names are RECOMMENDED to be:

  1. Third-person singular verb: VerifiesEmail
  2. Adjective: EmailVerifiable

MUST be in camelCase:

class QueryParser
{
public function sampleMethod(): void {}
public static function fromString(string $query): static {}
}

MUST be in snake_case:

function validate_input(): void {}

MUST be in snake_case, including class properties and static properties.

$query_parser = new QueryParser();
$query_parser->encoding_type = QueryParser::RFC3986;

Array variables SHOULD be plural:

$colors = ['green', 'yellow'];
$color = 'blue';

Associative arrays MUST use $values_by_key format:

$colors_by_person_name = [
'alice' => 'green',
'bob' => 'yellow',
];

2D associative arrays MUST use $value_lists_by_key format:

$color_lists_by_theme = [
'dark' => ['black', 'grey'],
'light' => ['white', 'green'],
];

foreach SHOULD use plural to singular:

foreach ($colors as $id => $color) {}
$login_user // currently logged-in user
$user // context user
$household // context household
$fqcn // fully-qualified class name, e.g. '\App\Models\Account'
$class_name // unqualified class name, e.g. 'Account'
$table_name // e.g. 'accounts'
$model // class name, in most cases $fqcn is preferred
$object // an instance of a class

MUST be in UPPERCASE_WITH_UNDERSCORES:

const ANONYMOUS_USER = 'anonymous';

MUST be in UPPERCASE_WITH_UNDERSCORES:

enum AccountType: string
{
case BANK = 'bank';
case CARD = 'card';
case INVESTMENT = 'investment';
case LOAN = 'loan';
case STOCK_PLAN = 'stock_plan';
}

Each method in a chain call is RECOMMENDED to start on a new line:

Foo::query()
->where(Foo::COLUMN_PARENT_ID, 1)
->where(Foo::COLUMN_TYPE, FooType::BAZ)
->where(function (Builder $query): void {
$query->whereNotIn(Foo::COLUMN_SUBTYPE, ['foo','bar','baz'])
->orWhereNull(Foo::COLUMN_SUBTYPE);
})
->pluck(Foo::COLUMN_NAME, Foo::COLUMN_ID)
->all();

Standard inline style:

$res = calculate($model, $param1, $param2, $param3);
$res = http_build_query($params, encoding_type: PHP_QUERY_RFC3986);

Vertical parameter list style for many parameters (trailing comma required):

$res = calculate(
$model,
$param1,
$param2,
$param3,
);

Named arguments MUST be aligned:

setcookie(
name : 'x-token',
value : $this->generateToken(),
expires_or_options: Date::now()->addSeconds($this->ttl)->timestamp(),
path : '/',
secure : true,
httponly : true,
);

All functions MUST have argument types and return types declared using the latest PHP standard.

// Void return type
function set(int $value): void
{
$this->var = $value;
}
// Union types
function get_user(int $id): User|null
{
// ...
}
// Intersection types
function create_reader(UnitEnum&FileTypeInterface $type): Reader
{
// ...
}

Comments MUST have the same indent as following statements:

// Check if authorized
if (Auth::check()) {
// Do the work
$this->do();
}
  • First word MUST be capitalized (unless at end of statement)
  • Space between // and content
// Capitalized comment
$fruit = 'apple'; // no need to capitalize

If a block comment contains PHPDoc notations, MUST use docblock style:

/**
* This is a comment, @link https://www.google.com/
*/

All code MUST pass PHP CS Fixer:

Terminal window
composer phpcs