php-best-practices by asyrafhussin/agent-skills
npx skills add https://github.com/asyrafhussin/agent-skills --skill php-best-practices现代 PHP 8.x 模式、PSR 标准、类型系统最佳实践和 SOLID 原则。包含 51 条编写清晰、可维护 PHP 代码的规则。
在提供任何建议之前,务必检查项目的 PHP 版本。 8.0 到 8.5 版本之间的功能差异很大。切勿建议项目版本中不存在的语法。
检查 composer.json 以获取所需的 PHP 版本:
{ "require": { "php": "^8.1" } } // -> 8.1 及以下版本的规则
{ "require": { "php": "^8.3" } } // -> 8.3 及以下版本的规则
{ "require": { "php": ">=8.4" } } // -> 8.4 及以下版本的规则
同时检查运行时版本:
php -v # 例如:PHP 8.3.12
| 功能 | 版本 | 规则前缀 |
|---|---|---|
| 联合类型、match 表达式、空安全运算符、命名参数、构造器属性提升、属性 | 8.0+ | type-、 |
广告位招租
在这里展示您的产品或服务
触达数万 AI 开发者,精准高效
modern-| 枚举、只读属性、交集类型、一等可调用对象、never 类型、纤程 | 8.1+ | modern- |
| 只读类、析取范式类型、独立 true/false/null 类型 | 8.2+ | modern- |
类型化类常量、#[\Override]、json_validate() | 8.3+ | modern- |
属性钩子、非对称可见性、#[\Deprecated]、省略括号的 new | 8.4+ | modern- |
| 管道运算符 ` | >` | 8.5+ |
仅建议在检测到的版本中可用的功能。 如果用户询问升级或新功能,请说明每个版本可用的内容。
在以下情况下参考这些指南:
| 优先级 | 类别 | 影响 | 前缀 | 规则数量 |
|---|---|---|---|---|
| 1 | 类型系统 | 关键 | type- | 9 |
| 2 | 现代 PHP 功能 | 关键 | modern- | 16 |
| 3 | PSR 标准 | 高 | psr- | 6 |
| 4 | SOLID 原则 | 高 | solid- | 5 |
| 5 | 错误处理 | 高 | error- | 5 |
| 6 | 性能 | 中 | perf- | 5 |
| 7 | 安全性 | 关键 | sec- | 5 |
type-strict-mode - 在每个文件中声明严格类型type-return-types - 始终声明返回类型type-parameter-types - 为所有参数指定类型type-property-types - 为类属性指定类型type-union-types - 有效使用联合类型type-intersection-types - 使用交集类型type-nullable-types - 正确处理可为空类型type-void-never - 为适当的返回类型使用 void/nevertype-mixed-avoid - 尽可能避免使用 mixed 类型8.0+:
modern-constructor-promotion - 构造器属性提升modern-match-expression - 使用 match 替代 switchmodern-named-arguments - 使用命名参数以提高清晰度modern-nullsafe-operator - 空安全运算符 (?->)modern-attributes - 使用属性处理元数据8.1+:
modern-enums - 使用枚举替代常量modern-enums-methods - 使用带方法和接口的枚举modern-readonly-properties - 为不可变数据使用只读属性modern-first-class-callables - 一等可调用对象语法modern-arrow-functions - 箭头函数(7.4+,与 8.1 功能配合良好)8.2+:
modern-readonly-classes - 只读类8.3+:
modern-typed-constants - 类型化类常量(const string NAME = 'foo')modern-override-attribute - 使用 #[\Override] 捕获父方法拼写错误8.4+:
modern-property-hooks - 使用属性钩子替代 getter/settermodern-asymmetric-visibility - 使用 public private(set) 实现受控访问8.5+:
modern-pipe-operator - 管道运算符 (|>) 用于函数式链式调用psr-4-autoloading - 遵循 PSR-4 自动加载规范psr-12-coding-style - 遵循 PSR-12 编码风格psr-naming-classes - 类命名约定psr-naming-methods - 方法命名约定psr-file-structure - 每个文件一个类psr-namespace-usage - 正确使用命名空间solid-srp - 单一职责原则:一个修改理由solid-ocp - 开闭原则:扩展而非修改solid-lsp - 里氏替换原则:子类型必须可替换solid-isp - 接口隔离原则:小而专注的接口solid-dip - 依赖倒置原则:依赖抽象error-custom-exceptions - 为不同错误创建特定的异常error-exception-hierarchy - 将异常组织成有意义的层次结构error-try-catch-specific - 捕获特定异常,而非通用的 \Exceptionerror-finally-cleanup - 使用 finally 保证资源清理error-never-suppress - 切勿使用 @ 错误抑制运算符perf-avoid-globals - 避免全局变量,使用依赖注入perf-lazy-loading - 延迟昂贵操作直到需要时perf-array-functions - 使用原生数组函数而非手动循环perf-string-functions - 使用原生字符串函数而非正则表达式perf-generators - 对大型数据集使用生成器sec-input-validation - 验证并清理所有外部输入sec-output-escaping - 根据上下文(HTML、JS、URL)转义输出sec-password-hashing - 使用 password_hash/verify,切勿使用 MD5/SHA1sec-sql-prepared - 对所有 SQL 查询使用预处理语句sec-file-uploads - 验证文件类型、大小、名称;存储在 Web 根目录之外有关详细示例和说明,请参阅规则文件:
<?php
declare(strict_types=1);
// 8.0+ 构造器属性提升 + 只读属性(8.1+)
class User
{
public function __construct(
public readonly string $id,
private string $email,
) {}
}
// 8.1+ 带方法的枚举
enum Status: string
{
case Active = 'active';
case Inactive = 'inactive';
public function label(): string
{
return match($this) {
self::Active => 'Active',
self::Inactive => 'Inactive',
};
}
}
// 8.0+ Match 表达式
$result = match($status) {
'pending' => 'Waiting',
'active' => 'Running',
default => 'Unknown',
};
// 8.0+ 空安全运算符
$country = $user?->getAddress()?->getCountry();
// 8.3+ 类型化类常量 + #[\Override]
class PaymentService extends BaseService
{
public const string GATEWAY = 'stripe';
#[\Override]
public function process(): void { /* ... */ }
}
// 8.4+ 属性钩子 + 非对称可见性
class Product
{
public string $name { set => trim($value); }
public private(set) float $price;
}
// 8.5+ 管道运算符
$result = $input
|> trim(...)
|> strtolower(...)
|> htmlspecialchars(...);
审计代码时,按此格式输出发现的问题:
file:line - [category] Description of issue
示例:
src/Services/UserService.php:15 - [type] Missing return type declaration
src/Models/Order.php:42 - [modern] Use match expression instead of switch
src/Controllers/ApiController.php:28 - [solid] Class has multiple responsibilities
阅读单独的规则文件以获取详细说明:
rules/modern-constructor-promotion.md
rules/type-strict-mode.md
rules/solid-srp.md
每周安装次数
886
代码仓库
GitHub 星标数
19
首次出现
2026年1月24日
安全审计
安装于
opencode766
codex750
gemini-cli745
github-copilot726
kimi-cli674
amp673
Modern PHP 8.x patterns, PSR standards, type system best practices, and SOLID principles. Contains 51 rules for writing clean, maintainable PHP code.
Always check the project's PHP version before giving any advice. Features vary significantly across 8.0 - 8.5. Never suggest syntax that doesn't exist in the project's version.
Check composer.json for the required PHP version:
{ "require": { "php": "^8.1" } } // -> 8.1 rules and below
{ "require": { "php": "^8.3" } } // -> 8.3 rules and below
{ "require": { "php": ">=8.4" } } // -> 8.4 rules and below
Also check the runtime version:
php -v # e.g. PHP 8.3.12
| Feature | Version | Rule Prefix |
|---|---|---|
| Union types, match, nullsafe, named args, constructor promotion, attributes | 8.0+ | type-, modern- |
| Enums, readonly properties, intersection types, first-class callables, never, fibers | 8.1+ | modern- |
| Readonly classes, DNF types, true/false/null standalone types | 8.2+ | modern- |
Typed class constants, #[\Override], json_validate() | 8.3+ | modern- |
Property hooks, asymmetric visibility, #[\Deprecated], new without parens | 8.4+ | modern- |
| Pipe operator ` | >` | 8.5+ |
Only suggest features available in the detected version. If the user asks about upgrading or newer features, mention what becomes available at each version.
Reference these guidelines when:
| Priority | Category | Impact | Prefix | Rules |
|---|---|---|---|---|
| 1 | Type System | CRITICAL | type- | 9 |
| 2 | Modern PHP Features | CRITICAL | modern- | 16 |
| 3 | PSR Standards | HIGH | psr- | 6 |
| 4 | SOLID Principles | HIGH | solid- |
type-strict-mode - Declare strict types in every filetype-return-types - Always declare return typestype-parameter-types - Type all parameterstype-property-types - Type class propertiestype-union-types - Use union types effectivelytype-intersection-types - Use intersection typestype-nullable-types - Handle nullable types properlytype-void-never - Use void/never for appropriate return typestype-mixed-avoid - Avoid mixed type when possible8.0+:
modern-constructor-promotion - Constructor property promotionmodern-match-expression - Match over switchmodern-named-arguments - Named arguments for claritymodern-nullsafe-operator - Nullsafe operator (?->)modern-attributes - Attributes for metadata8.1+:
modern-enums - Enums instead of constantsmodern-enums-methods - Enums with methods and interfacesmodern-readonly-properties - Readonly for immutable datamodern-first-class-callables - First-class callable syntaxmodern-arrow-functions - Arrow functions (7.4+, pairs well with 8.1 features)8.2+:
modern-readonly-classes - Readonly classes8.3+:
modern-typed-constants - Typed class constants (const string NAME = 'foo')modern-override-attribute - #[\Override] to catch parent method typos8.4+:
modern-property-hooks - Property hooks replacing getters/settersmodern-asymmetric-visibility - public private(set) for controlled access8.5+:
modern-pipe-operator - Pipe operator (|>) for functional chainingpsr-4-autoloading - Follow PSR-4 autoloadingpsr-12-coding-style - Follow PSR-12 coding stylepsr-naming-classes - Class naming conventionspsr-naming-methods - Method naming conventionspsr-file-structure - One class per filepsr-namespace-usage - Proper namespace usagesolid-srp - Single Responsibility: one reason to changesolid-ocp - Open/Closed: extend, don't modifysolid-lsp - Liskov Substitution: subtypes must be substitutablesolid-isp - Interface Segregation: small, focused interfacessolid-dip - Dependency Inversion: depend on abstractionserror-custom-exceptions - Create specific exceptions for different errorserror-exception-hierarchy - Organize exceptions into meaningful hierarchyerror-try-catch-specific - Catch specific exceptions, not generic \Exceptionerror-finally-cleanup - Use finally for guaranteed resource cleanuperror-never-suppress - Never use @ error suppression operatorperf-avoid-globals - Avoid global variables, use dependency injectionperf-lazy-loading - Defer expensive operations until neededperf-array-functions - Use native array functions over manual loopsperf-string-functions - Use native string functions over regexperf-generators - Use generators for large datasetssec-input-validation - Validate and sanitize all external inputsec-output-escaping - Escape output based on context (HTML, JS, URL)sec-password-hashing - Use password_hash/verify, never MD5/SHA1sec-sql-prepared - Use prepared statements for all SQL queriessec-file-uploads - Validate file type, size, name; store outside web rootFor detailed examples and explanations, see the rule files:
<?php
declare(strict_types=1);
// 8.0+ Constructor promotion + readonly (8.1+)
class User
{
public function __construct(
public readonly string $id,
private string $email,
) {}
}
// 8.1+ Enums with methods
enum Status: string
{
case Active = 'active';
case Inactive = 'inactive';
public function label(): string
{
return match($this) {
self::Active => 'Active',
self::Inactive => 'Inactive',
};
}
}
// 8.0+ Match expression
$result = match($status) {
'pending' => 'Waiting',
'active' => 'Running',
default => 'Unknown',
};
// 8.0+ Nullsafe operator
$country = $user?->getAddress()?->getCountry();
// 8.3+ Typed class constants + #[\Override]
class PaymentService extends BaseService
{
public const string GATEWAY = 'stripe';
#[\Override]
public function process(): void { /* ... */ }
}
// 8.4+ Property hooks + asymmetric visibility
class Product
{
public string $name { set => trim($value); }
public private(set) float $price;
}
// 8.5+ Pipe operator
$result = $input
|> trim(...)
|> strtolower(...)
|> htmlspecialchars(...);
When auditing code, output findings in this format:
file:line - [category] Description of issue
Example:
src/Services/UserService.php:15 - [type] Missing return type declaration
src/Models/Order.php:42 - [modern] Use match expression instead of switch
src/Controllers/ApiController.php:28 - [solid] Class has multiple responsibilities
Read individual rule files for detailed explanations:
rules/modern-constructor-promotion.md
rules/type-strict-mode.md
rules/solid-srp.md
Weekly Installs
886
Repository
GitHub Stars
19
First Seen
Jan 24, 2026
Security Audits
Gen Agent Trust HubPassSocketPassSnykPass
Installed on
opencode766
codex750
gemini-cli745
github-copilot726
kimi-cli674
amp673
React 组合模式指南:Vercel 组件架构最佳实践,提升代码可维护性
102,200 周安装
Gemini Interactions API 指南:统一接口、智能体交互与服务器端状态管理
833 周安装
Apollo MCP 服务器:让AI代理通过GraphQL API交互的完整指南
834 周安装
智能体记忆系统构建指南:分块策略、向量存储与检索优化
835 周安装
Scrapling官方网络爬虫框架 - 自适应解析、绕过Cloudflare、Python爬虫库
836 周安装
抽奖赢家选取器 - 随机选择工具,支持CSV、Excel、Google Sheets,公平透明
838 周安装
Medusa 前端开发指南:使用 SDK、React Query 构建电商商店
839 周安装
| 5 |
| 5 | Error Handling | HIGH | error- | 5 |
| 6 | Performance | MEDIUM | perf- | 5 |
| 7 | Security | CRITICAL | sec- | 5 |