资讯动态

PSR-5 PHPDoc 标准全面解读:DocBlock 语法形式与 Type 类型系统的正式定义

发布时间:2026/10/6 1:53:37 来源:尧图企业网站定制
文档开发工具【免费下载链接】fig-standardsStandards either proposed or approved by the Framework Interop Group项目地址https://gitcode.com/gh_mirrors/fi/fig-standards点击查看免费下载导读本文以 PHP-FIG 仓库中的 proposed/phpdoc.md即PSR-5: PHPDoc草案为核心系统讲解 PHPDoc 的正式定义从 DocComment、DocBlock、Structural Element 等基础概念到 Summary、Description、Tags 的 ABNF 语法形式再到附录 A 中涵盖 union/intersection 类型与 17 个关键字的 Type 类型系统。读完本文你将能够精确区分 PHPDoc 与 DocBlock、按规范书写可被机器解析的多行/单行文档块并正确使用int[]、(int|string)[]、self、static、$this、never等类型表达式。1. 背景为什么需要一份 PHPDoc 的正式标准PHPDoc 记法最早由 Ulf Wendel 于 2000 年提出深受 JavaDoc 启发如今已被 PHP 社区大量公共项目广泛使用详见 proposed/phpdoc-meta.md。尽管 phpDocumentor 等工具长期推动了 PHPDoc 记法的发展但随着 IDE、静态分析器、文档生成器等越来越多工具共同消费这一记法其长期依赖的 de-facto事实标准地位已经不能满足需求因此需要一个正式标准。从 PSR.md 的 Draft 列表可以看到PSR-5PHPDoc Standard与 PSR-19PHPDoc tags目前都处于Draft草案状态编辑者均为 Chuck Burgess赞助人为 Michael Cullum。这意味着文档内容仍在演进之中但其中对语法形式的定义已经非常完整。按照 proposed/phpdoc-meta.md 的定位本标准的目标是提供 PHPDoc 记法的完整技术定义schema引入与当今最佳实践、设计模式匹配的新概念。其非目标是不提供何时以及如何使用的建议——它不是一份编码规范coding standard。这一点决定了 PSR-5 通篇使用 RFC 2119 中的 MUST / SHOULD / MAY 等关键词来界定语法义务而不是审美偏好。2. 核心概念定义PHPDoc 与 DocBlock 是两个不同的实体PSR-5 在Definitions章节给出了六个关键定义其中最重要的一条是PHPDoc 与 DocBlock 是两个独立的实体。DocBlock 是DocComment一种注释与PHPDoc 实体的组合而真正包含本文档所描述语法如 Description 和 Tags的是 PHPDoc 实体本身。2.1 Structural Element结构元素可被 DocBlock 前置修饰的编程构造集合包括require/include以及它们的\_once变体class/interface/traitfunction独立函数与类方法变量局部与全局作用域与类属性常量通过define定义的全局常量与类常量规范RECOMMENDED推荐在 Structural Element 定义处前置 DocBlockDocBlock 习惯上紧贴元素但MAY可以被任意数量的空行隔开。下面是三种情况的对照/** * This is a counter. * var int $int */ $int 0; /** var int $int This is a counter. */ $int 0; /* comment block... this is not a docblock */ $int; // single line comment... this is not a docblock $int;类内定位的示例/** * This class shows an example on where to position a DocBlock. */ class Foo { /** var ?string $title contains a title for the Foo */ protected $title null; /** * Sets a single-line title. * * param string $title A text for the title. * * return void */ public function setTitle($title) { // there should be no docblock here $this-title $title; } }关于复合声明compound statements规范特别提醒NOT RECOMMENDED不建议对常量或属性使用复合定义因为 DocBlock 在这种场景下的处理可能产生意外结果。若必须使用复合语句每个元素SHOULD应当有前置的 DocBlockclass Foo { protected /** * var string Should contain a name */ $name, /** * var string Should contain a description */ $description; }2.2 DocComment文档注释一种特殊类型的注释MUST必须以字符序列/**加一个空白字符开头以*/结尾中间可以有零行或多行内容。多行 DocComment 中每一行MUST以星号*开头且SHOULD与开头子句的第一个星号对齐/** ... *//** * ... */2.3 DocBlock文档块DocBlock 是包含单个 PHPDoc 结构的 DocComment是代码内最基本的表示形式。2.4 Tag标签关于某个 Structural Element 的单条元信息。例如param string $argument1 This is a parameter.中param是标签名string $argument1 This is a parameter.是元数据。2.5 Type类型决定与某个元素关联的数据类型基本类型、类、对象用于确定参数、属性、常量等的确切数据类型详见本文第 6 节对应原文档附录 A。2.6 FQSEN全限定结构元素名FQSENFully Qualified Structural Element Name是 FQCN全限定类名的扩展它把 FQCN 的原则推广到接口、Trait、函数和全局常量并加入标识类/接口/Trait 成员的记法。各类型结构元素的记法如下结构元素类型FQSEN 记法命名空间Namespace\My\Space函数Function\My\Space\myFunction()常量Constant\My\Space\MY_CONSTANT类Class\My\Space\MyClass接口Interface\My\Space\MyInterfaceTrait\My\Space\MyTrait方法Method\My\Space\MyClass::myMethod()属性Property\My\Space\MyClass::$my_property类常量Class Constant\My\Space\MyClass::MY_CONSTANTFQSEN 的 ABNF 定义如下语法符号遵循 RFC 5234FQSEN fqnn / fqcn / constant / method / property / function fqnn \ [name] *(\ [name]) fqcn fqnn \ name constant ((fqnn \) / (fqcn ::)) name method fqcn :: name () property fqcn ::$ name function fqnn \ name () name (ALPHA / _) *(ALPHA / DIGIT / _)3. 基本准则Basic PrinciplesPSR-5 用两条 MUST 级规则界定了最基本的约束一个 PHPDocMUST 总是被包含在 DocComment 中二者的组合称为 DocBlock。一个 DocBlockMUST 直接前置于一个 Structural Element。4. PHPDoc 格式The PHPDoc FormatPHPDoc 格式的 ABNF 定义是整个规范的核心它明确了摘要 描述 标签三段式结构PHPDoc [summary [description]] [tags] eol [CR] LF ; to compatible with PSR-12 summary 1*CHAR 2*eol description 1*(CHAR / inline-tag) 1*eol ; any amount of characters ; with inline tags inside tags *(tag 1*eol) inline-tag { tag } tag tag-name [: tag-specialization] [tag-details] tag-name (ALPHA / \) *(ALPHA / DIGIT / \ / - / _) tag-specialization 1*(ALPHA / DIGIT / -) tag-details (1*SP tag-description) tag-description (CHAR / inline-tag) *(CHAR / inline-tag / eol) tag-argument *SP 1*CHAR [,] *SP值得注意的语法细节行结束符eol被定义为[CR] LF即与PSR-12accepted/PSR-12-extended-coding-style-guide.md保持一致使用 LF 换行inline-tag由花括号包裹的 tag 构成形如{link ...}tag 的tag-name允许以\开头这正是第 5.4 节示例中\Doctrine\Orm\Mapper\Entity()这类注解annotation风格标签得以书写的原因tag-specialization标签特化与tag-details均为可选部分。4.1 Summary摘要MUST包含对 Structural Element 目的的抽象概括RECOMMENDED只占一行或两行不要更多除非它是 PHPDoc 中唯一的内容否则MUST以两个连续换行结尾如果提供了 Description则必须先有 Summary否则 Description 有被误认为 Summary 的风险由于 Summary 类似章节标题RECOMMENDED尽量少用格式化与 Description 不同规范不要求为 Summary 支持标记语言。4.2 Description描述Description 是OPTIONAL可选的但SHOULD在 Structural Element 的复杂度超出 Summary 能表达的范畴时包含。任何解析 Description 的应用程序RECOMMENDED支持Markdown标记语言以便作者提供格式化和清晰的代码示例。Description 的常见用途提供比 Summary 更详细的方法行为说明说明一个数组/对象由哪些子元素构成提供一组常见用例或适用场景。4.3 Tags标签Tags 为 Structural Element 提供简明元数据。每个标签以新行开始后面紧跟符号和标签名然后是空白字符和元数据含描述。元数据如果提供MAY跨多行并COULD遵循该标签规定的严格格式。以param string $argument1 This is a parameter.为例它由一个名称param和元数据string $argument1 This is a parameter.组成其中元数据又拆分为类型string、变量名$argument1和描述This is a parameter.。Tag 的描述MUST支持 Markdown 作为格式化语言且描述MAY与标签同行或另起一行。下面三种写法语义完全相同/** * var string This is a description. * var string This is a * description. * var string * This is a description. */需要强调的是此定义不适用于注解Annotation标签——注解不在 PSR-5 的范围内。4.3.1 Tag Name标签名标签名表明该标签所承载信息的类型。标签名的完整列表与各自语法由配套的PSR-19PHPDoc tags提供见 proposed/phpdoc-tags.md。PSR-19 按目录形式收录了api、author、copyright、deprecated、generated、internal、link、method、package、param、property、return、see、since、throws、todo、uses、var、version共 19 个标签的语法与语义并定义了继承规则例如author、copyright、version为所有结构元素强制继承的标签。4.4 完整示例Examples一个完整的 DocBlock 可以是这样的/** * This is a Summary. * * This is a Description. It may span multiple lines * or contain code examples using the _Markdown_ markup * language. * * see Markdown * * param int $parameter1 A parameter description. * param \Exception $e Another parameter description. * * \Doctrine\Orm\Mapper\Entity() * * return string */ function test($parameter1, $e) { ... }Description 可以省略/** * This is a Summary. * * see Markdown * * param int $parameter1 A parameter description. * param \Exception $parameter2 Another parameter description. * * \Doctrine\Orm\Mapper\Entity() * * return string */ function test($parameter1, $parameter2) { }Tags 也可以省略/** * This is a Summary. */ function test($parameter1, $parameter2) { }DocBlock 还可以只占一行/** var \ArrayObject $array An array of things. */ public $array null;5. 结合 PSR-19 理解标签体系虽然 PSR-5 本身只定义标签的语法形式 标签名 可选特化 可选细节但标签的语义目录由 proposed/phpdoc-tags.mdPSR-19承载。二者是一对配合使用的草案PSR-5 提供机器可解析的语法骨架PSR-19 逐个定义标签的 Syntax、Description 与 Examples。例如param的语法为param [Type] [...]$[name] [description]其中类型是 MUST 提供的描述可选但推荐return语法为return Type [description]且规定若未给出return类型、签名中也未声明返回类型解释器 MUST 视同提供了return mixed。这种语法 目录的分工正体现了 PSR-5 为未来标签扩展预留空间的整体设计详见 proposed/phpdoc-meta.md 中的Chosen Approach。6. 附录 ATypes类型系统6.1 ABNF 定义Type 的 ABNF 定义为type-expression type *(| type) *( type) type class-name / keyword / array array (type / array-expression) [] array-expression ( type-expression ) class-name [\] label *(\ label) label (ALPHA / %x7F-FF) *(ALPHA / DIGIT / %x7F-FF) keyword array / bool / callable / false / float / int / iterable / mixed / never keyword / null / object / resource / self / static / string / true / void / $this6.2 联合类型与交叉类型Union / Intersection当 Type 由多个类型组成时MUST用竖线|联合类型或与号交叉类型分隔。任何支持本规范的解析器MUST先识别并拆分 Type再进行求值。联合类型示例return int|null交叉类型示例var \MyClass\PHPUnit\Framework\MockObject\MockObject $myMockObject交叉类型在实践中的典型用法是标注既是业务类实例、又是 Mock 对象的双重身份——这正是测试替身在静态分析中的常见需求。6.3 数组ArraysType 所代表的值可以是数组必须按以下三种方式之一定义未指定内容不给数组内容定义。 示例return array指定为单一类型每个数组成员是同一类型。 示例return int[]注意mixed也是单一类型因此可显式表示每个成员可以是任意类型。指定为多个显式类型每个成员可以是给定类型中的任意一种。 示例return (int|string)[]第三种写法依赖 ABNF 中的array-expression ( type-expression )即用圆括号先组合联合类型、再整体加[]。6.4 合法类名Valid Class Name类名的合法性取决于 Type 被提及的上下文它可以是全限定类名FQCN也可以是命名空间中的局部名。该 Type 所适用的元素要么是该类的实例要么是该类子类/后代类的实例。规范 RECOMMENDED收集并整理这类信息的应用如 IDE、文档生成器应在类的每次出现处展示其子类列表让使用者更清楚哪些类可作为该类型。6.5 关键字Keyword详解关键字用于界定 Type 的用途——并非每个元素都由类决定但仍有必要分类以帮助开发者理解 DocBlock 覆盖的代码。规范特别提醒PHP 中部分关键字允许作为类名难以与真实类区分因此关键字 MUST 使用小写多数类名以大写字母开头同时RECOMMENDED不要在代码中使用这些名字的类。PSR-5 识别的 17 个关键字bool适用元素只有TRUE或FALSE两种状态。int适用元素是整数whole number / integer。float适用元素是连续数实数。string适用元素是二进制字符串。object适用元素是某个未确定类的实例。array适用元素是值的数组。iterable适用元素是数组或 Traversable 对象按 PHP 对 iterable 的定义。resource适用元素是资源按 PHP 对 resource 的定义。mixed适用元素可以是本规范所列的任何类型编译期无法确定具体类型。void通常只用于方法/函数的返回类型表示不返回任何内容使用者不应依赖返回值。/** * return void */ function outputHello() { echo Hello world; }null适用元素是NULL值技术上即不存在。与void的区别在于null可用于任何在特定时刻可能显式包含NULL值的场景。/** * return null */ function foo() { echo Hello world; return null; }/** * param bool $create_new When true returns a new stdClass. * * return stdClass|null */ function foo($create_new) { if ($create_new) { return new stdClass(); } return null; }callable适用元素是指向函数调用的指针可以是 PHP 定义的任何 callable 形态。false/true适用元素将恰好取TRUE或FALSE值不会返回其他值。self适用元素与被文档化元素最初所在的那个类是同一个类。 示例方法c位于类A中DocBlock 声明其返回类型为self则方法c返回类A的实例。当涉及继承时可能产生歧义——类B继承类A且未重定义方法cself可被理解为类A或类B。规范规定此时selfMUST 被解释为书写包含该 self 类型的 DocBlock 所在的类即上例中始终指类A。同样地规范 RECOMMENDED 应用在展示时列出子类列表。static适用元素是被文档化元素所在类的实例但当在子类中遇到时则是该子类的实例而非原始类。其行为与 PHP 的后期静态绑定late static binding关键字一致注意不是 static 方法/属性/变量的修饰符。$this适用元素是给定上下文中当前类完全相同的那个实例。它是比static更严格的版本——返回的实例不仅必须是同类还必须是同一实例。该类型常用于标注实现Fluent Interface流式接口设计模式的方法返回值。never表示元素不会返回任何东西且总是抛出异常或以异常方式终止程序例如调用exit。7. 关键要点总结PHPDoc ≠ DocBlockDocBlock DocComment PHPDoc 实体语法规则作用于 PHPDoc 实体本身。结构骨架固定PHPDoc [summary [description]] [tags]Summary 以两个换行结尾Description 支持 MarkdownTags 以开头。类型系统完备支持类名、17 个关键字、数组含(int|string)[]复合写法、联合类型|与交叉类型。继承语义在 PSR-19 中定义如param、return、throws、var、package等标签具有元素类型专属的继承规则inheritDoc与{inheritDoc}用于显式继承。对于需要实现 PHPDoc 解析器、或希望让自己的 IDE/静态分析工具文档行为与社区标准对齐的开发者可直接以 proposed/phpdoc.md 为语法基准配合 proposed/phpdoc-tags.md 的标签目录使用同时注意当前两文档均为Draft状态见 PSR.md内容仍可能随工作组的修订而变化。赞分享文档开发工具【免费下载链接】fig-standardsStandards either proposed or approved by the Framework Interop Group项目地址https://gitcode.com/gh_mirrors/fi/fig-standards点击查看免费下载相关推荐Penrose Domain 类型声明全解type 语法、子类型体系与字面量类型约束Penrose Domain 类型声明全解type 语法、子类型体系与字面量类型约束 本文围绕 Penrose 的 Domain 类型系统展开类型是 Pen开发工具数据可视化从0到1使用MASA Blazor Pro构建企业级Web应用从0到1使用MASA Blazor Pro构建企业级Web应用 MASA Blazor是一个基于Material Design的Blazor UI组件库支持UI库/组件前端MindIE/stable_diffusion_v1.5终极指南AI绘图模型从入门到精通MindIE/stable_diffusion_v1.5终极指南AI绘图模型从入门到精通 MindIE/stable_diffusion_v1.5是一款强大的上一篇GitHub_Trending/ge/generative-models的梯度检查点节省显存训练策略下一篇Dism-Multi-language测试环境搭建虚拟机与物理机配置创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑