PHPackages                             jared/php-docblock-parser - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Utility &amp; Helpers](/categories/utility)
4. /
5. jared/php-docblock-parser

ActiveLibrary[Utility &amp; Helpers](/categories/utility)

jared/php-docblock-parser
=========================

Parses docblocks

010PHP

Since Sep 14Pushed 2y ago1 watchersCompare

[ Source](https://github.com/JaredSpb/php-docblock-parser)[ Packagist](https://packagist.org/packages/jared/php-docblock-parser)[ RSS](/packages/jared-php-docblock-parser/feed)WikiDiscussions main Synced 1mo ago

READMEChangelogDependenciesVersions (1)Used By (0)

php-docblock-parser
===================

[](#php-docblock-parser)

This a standalone library for parsing docblocks. Only PHPDoc v3 are supported at the moment.

Installation
------------

[](#installation)

```
composer require jared/php-docblock-parser

```

Usage
-----

[](#usage)

```
$raw = '/**
* The summary string
* having two lines.
* The description with a {@link proto://domain.tld The Link} element.
* @method int[]|Some\Class myMethod(int[] $param1, SomeType|null $param2) and method description
* @param int[] $param1 Param description
* @param Some\Class $param2 Param2 description
*                           having two lines
* @return mixed[] return description
* @see Something\Here
*/';

$docblock = new Falloff\DocBlock\PHPDoc( $raw );

foreach( $docblock as $index => $element )
	print_r($element);
```

Traversing
----------

[](#traversing)

### Direct access

[](#direct-access)

The parsed docblock is a recursive structure consisting of text blocks and tag structures. The latter may contain own text blocks that might contain inline tags, that might contain... This structure might be traversed without additional tools in the following way:

```
$queue = [$docblock];

while( !empty( $queue ) ){

    $element = array_shift($queue);

	if( is_object($element) and get_class( $element ) == Falloff\DocBlock\PHPDoc\TextBlock::class ){
		// Gives 'The cummary string....'
		print $element->summary[0] . "\n";

		// Gives 'The Description...'
		print $element->text[0] . "\n";

		// Refers to Placeholder object, containing the Link tag
		print get_class($element->text[1]) . "\n";

		// The 'proto://domain.tld' string
		print $element->text[1]->tag->url . "\n";

		// The 'The Link' string
		print $element->text[1]->tag->description[0] . "\n";
	}

	if( is_object($element) and get_class( $element ) == Falloff\DocBlock\PHPDoc\Tag\Method::class ){
		 // The 'int[]|Some\Class' string
		print $element->type . "\n"; ;

		 // 'myMethod'
		print $element->definition->name . "\n"; ;

		// The params are accessed like the `definition` was an array:

		// 'int[]'
		print $element->definition[0]->type . "\n";
		 // '$param1'
		print $element->definition[0]->name . "\n";
	}

	// Adding param's tags descriptions to the queue
	if( is_object($element) and get_class( $element ) == Falloff\DocBlock\PHPDoc\Tag\Param::class ){

		// Elements in the description might be objects or regular strings
		foreach( $element->description as $param_description_chunk ){
			$queue[] = $param_description_chunk;
		}
	}

	if( is_scalar($element) ){
		// Will produce following two strings:
		// 'The following is a regular scalar string: `Param description`'
		// 'The following is a regular scalar string: `Param2 description`''
		print 'The following is a regular scalar string: `' . $element . "`\n";
	}

	if( is_object($element) ){
	    foreach ($element as $child) {
	        $queue[] = $child;
	    }
	}

}
```

This approach might be used in some cases, but is looks pretty inconvinient.

### Via Visitor

[](#via-visitor)

This package ships the `Visitor` interface that might be used to make traversal easier:

```
$visitor = new class implements Falloff\DocBlock\Visitor{

	function in( Falloff\DocBlock\Entity|string|null $entity, array $payload, int|string $idx ) {

		print 'Index is: ' . $idx . "\n";

		print (
			is_object( $entity )
			? "Entity is an object of class " . get_class( $entity ) . "\n"
			: (
				is_null( $entity )
				? "Entity is NULL\n"
				: "Entity is a string containing: " . $entity . "\n"
			)
		);

		print "Payload is: \n";
		print_r($payload);

		print "\n";

		return true;

	}

	function out( Falloff\DocBlock\Entity|string|null $entity, array $payload, int|string $idx){}
};

$docblock->visit( $visitor );
```

The visitor must implement the `in` and `out` methods. In the traversal process these methods are called with the current entity itself, which might be the instance representing the docblock or its component. The `$payload` param is an array containing some internal structure of the current element, like a `name` and `type` of the `@param` tag. The `$idx` param is an index of a current element inside its parent structure. This might be integer for plain containers like `Text`, or a name of a property like `url` for `@link` tag. The return value of the `in` method matters in the following way:

- pure `false` value tells to stop traversing current element, its children or properties and move to the next element in the tree
- pure `true` value tells to traverse through current element properties i.e. the `ref` and `description` for the `@see` tag
- any other value will make traversal skip element's properties and move to the element's children if any, or just move forward otherwise

Traversing without returning a value should be enough while `$payload` contains all the data required to process the element. If thats not enough, make sure to return `true` to access the element's properties in the next iteration.

###  Health Score

14

—

LowBetter than 2% of packages

Maintenance20

Infrequent updates — may be unmaintained

Popularity5

Limited adoption so far

Community7

Small or concentrated contributor base

Maturity21

Early-stage or recently created project

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

### Community

Maintainers

![](https://www.gravatar.com/avatar/b429117d3670af5a4be542223331c8239d40db8f5f5fd20edde449f15783f7ef?d=identicon)[JaredSpb](/maintainers/JaredSpb)

---

Top Contributors

[![JaredSpb](https://avatars.githubusercontent.com/u/26169319?v=4)](https://github.com/JaredSpb "JaredSpb (9 commits)")

### Embed Badge

![Health badge](/badges/jared-php-docblock-parser/health.svg)

```
[![Health](https://phpackages.com/badges/jared-php-docblock-parser/health.svg)](https://phpackages.com/packages/jared-php-docblock-parser)
```

###  Alternatives

[isolate/unit-of-work

Unit of Work

2323.1k5](/packages/isolate-unit-of-work)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
