Compare commits

...
832 Commits
Author SHA1 Message Date
Jaap van Otterdijk 9ce38cc175 Merge pull request #440 from williamdes/patch-1
Update .gitattributes
2026-01-23 08:19:12 +01:00
William Desportes 8bd689392b Update .gitattributes 2026-01-22 20:20:51 +00:00
Jaap van Otterdijk 2f5cbed597 Merge pull request #438 from mspirkov/fix-standard-tag-factory-2
Fix the creation of tags with types in `StandardTagFactory`
2026-01-20 16:30:42 +01:00
Максим Спирков ab84cf5938 Fix merge issues 2026-01-20 18:39:52 +04:00
Maksim Spirkov a1663cff71 Merge branch 'phpDocumentor:6.x' into fix-standard-tag-factory-2 2026-01-20 18:38:07 +04:00
Jaap van Otterdijk 2ae140d7b6 Merge pull request #437 from stof/patch-1
Register 'mixin' tag handler in StandardTagFactory
2026-01-20 15:32:29 +01:00
Максим Спирков f80ca7adb3 Fix CS 2026-01-20 16:34:39 +04:00
Максим Спирков d14f75039d Add data sets for test 2026-01-20 16:34:18 +04:00
Максим Спирков 897592cd9e Fix CS 2026-01-20 16:19:35 +04:00
Максим Спирков f31a3bb769 Fix CS 2026-01-20 16:18:31 +04:00
Максим Спирков 6d6d80ca90 Fix CS 2026-01-20 16:16:51 +04:00
Максим Спирков b5676cd554 Fix the creation of tags with types in StandardTagFactory 2026-01-20 16:10:37 +04:00
Christophe Coevoet d23ba2c82e Register 'mixin' tag handler in StandardTagFactory 2026-01-20 12:38:09 +01:00
Jaap van Otterdijk 0d14a1acef Merge pull request #436 from stof/patch-1
Fix the markup of the upgrade documentation
2026-01-19 21:30:55 +01:00
Christophe Coevoet 78cadfb570 Fix the markup of the upgrade documentation 2026-01-18 21:19:51 +01:00
Jaapio 02600c041e Add upgrade docs 2026-01-07 21:22:53 +01:00
Jaap van Otterdijk 721f1e766d Merge pull request #433 from mspirkov/update-type-resolver
Bump `phpdocumentor/type-resolver` from 2.x-dev to 2.0
2026-01-07 20:49:45 +01:00
Максим Спирков 99d8d436bf Bump phpdocumentor/type-resolver from 2.x-dev to 2.0 2026-01-07 14:40:05 +04:00
Jaapio 115060b762 Improve doc titles 2026-01-05 22:45:19 +01:00
Jaapio 5e61e4f9ff Secret token 2026-01-05 22:21:57 +01:00
Jaapio 48505d477c Add bot token for deployment 2026-01-05 22:07:19 +01:00
Jaap van Otterdijk da3c60da16 Merge pull request #432 from phpDocumentor/docs
Add docs
2026-01-05 21:53:28 +01:00
Jaapio febafae9b0 Add auto deploy 2026-01-05 21:52:34 +01:00
Jaapio cd04bb47b5 Add docs 2026-01-05 20:49:06 +01:00
Jaap van Otterdijk 92ecf5dcfd Merge pull request #431 from phpDocumentor/phpstan-improvements
More phpstan checks for better code
2026-01-04 16:27:49 +01:00
Jaapio 9f96a9ff69 Add missing tests 2026-01-04 16:26:03 +01:00
Jaapio b9d1e48bd6 Add phpstan baseline to ignore unused code 2026-01-04 16:24:55 +01:00
Jaapio c1111a0b0a Add tests for factories 2026-01-04 15:34:19 +01:00
Jaapio 3f6d648d7d More phpstan checks for better code 2026-01-01 22:36:45 +01:00
Jaap van Otterdijk f08359470f Merge pull request #430 from phpDocumentor/cleanup/method-deprecations
Remove deprecated arguments
2026-01-01 20:58:40 +01:00
Jaapio bff00aaf74 Remove deprecated arguments
Argument creation was deprecated on the method tag. This is now removed.
2026-01-01 20:56:36 +01:00
Jaap van Otterdijk 7f416fbc30 Merge pull request #429 from phpDocumentor/prepare-6.x-build
Prepare 6.x build
2025-12-28 11:05:29 +01:00
Jaapio fba45a3718 More cleanup of tag creation
TagWithType need to be created via a factory now.
2025-12-24 16:16:59 +01:00
Jaapio 02f9ed7a8f Remove deprecated code paths
Typed tags are no longer creatable via the create method. The
parsing has become to complex to handle per tag. This logic has been
moved into factories.
2025-12-23 21:51:08 +01:00
Jaapio 889d86b8b0 Remove support of eol versions of dependencies
We need to move on.
2025-12-23 21:16:28 +01:00
Jaapio 97db20d534 Tests with type resolver v2 2025-12-22 23:04:25 +01:00
Jaapio d075d95973 Upgrade workflow for 6.x 2025-12-22 23:02:14 +01:00
Jaap van Otterdijk 5cee1d3dfc Merge pull request #425 from simPod/wm-2
chore(deps): allow webmozart/assert v2
2025-12-22 22:13:58 +01:00
Simon Podlipsky f9534dfb4b chore(deps): allow webmozart/assert v2 2025-12-22 20:06:07 +01:00
Jaap van Otterdijk 90614c73d3 Merge pull request #422 from sbuerk/stefan-1
[BUGFIX] Mitigate "Using null as an array offset is deprecated"
2025-11-27 20:50:05 +01:00
Jaap van Otterdijk 4663249fef Merge pull request #423 from phpDocumentor/remove-outdated-test
Remove outdated test
2025-11-27 20:49:31 +01:00
Jaapio 84265c845d Remove outdated test
We support collections of self now.
2025-11-27 20:45:57 +01:00
Stefan Bürk 67d330993f [BUGFIX] Mitigate "Using null as an array offset is deprecated"
Using `DocBlockFactory->create()` with a phpdocblock
hanging a `@throws` tag followed by a exception class
name emits following PHP 8.5.0 deprecation:

```
Using null as an array offset is deprecated,
use an empty string instead
```

in `StandardTagFactory->getArgumentsForParametersFromWiring()`.

This change uses the null-coalsce operator to fallback to
an empty string for the value which should be used as an
array key instead of using `null` to mitigate the deprecation
notice with PHP8.5.0 and matches the behaviour in earlier
PHP versions without the deprecation message.
2025-11-26 22:06:27 +01:00
Jaap van Otterdijk 90a04bcbf0 Merge pull request #421 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/code-coverage.yml-0.9
Bump phpDocumentor/.github/.github/workflows/code-coverage.yml from 0.8 to 0.9
2025-11-17 22:13:10 +01:00
dependabot[bot] cdfe60ba03 Bump phpDocumentor/.github/.github/workflows/code-coverage.yml
Bumps [phpDocumentor/.github/.github/workflows/code-coverage.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/code-coverage.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-17 10:29:13 +00:00
Jaap van Otterdijk c733f0398f Merge pull request #418 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/continuous-integration.yml-0.9
Bump phpDocumentor/.github/.github/workflows/continuous-integration.yml from 0.8 to 0.9
2025-11-10 16:53:48 +01:00
Jaap van Otterdijk 70bed89108 Merge pull request #416 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/dependency-analysis.yml-0.9
Bump phpDocumentor/.github/.github/workflows/dependency-analysis.yml from 0.8 to 0.9
2025-11-10 16:53:32 +01:00
Jaap van Otterdijk 831a7596d5 Merge pull request #417 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/coding-standards.yml-0.9
Bump phpDocumentor/.github/.github/workflows/coding-standards.yml from 0.8 to 0.9
2025-11-10 16:53:12 +01:00
Jaap van Otterdijk e9a766338b Merge pull request #420 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/lint.yml-0.9
Bump phpDocumentor/.github/.github/workflows/lint.yml from 0.8 to 0.9
2025-11-10 16:52:55 +01:00
Jaap van Otterdijk b181f1c190 Merge pull request #419 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github/dot-github/workflows/static-analysis.yml-0.9
Bump phpDocumentor/.github/.github/workflows/static-analysis.yml from 0.8 to 0.9
2025-11-10 12:38:13 +01:00
dependabot[bot] 121ae15001 Bump phpDocumentor/.github/.github/workflows/lint.yml from 0.8 to 0.9
Bumps [phpDocumentor/.github/.github/workflows/lint.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/lint.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-10 11:29:34 +00:00
dependabot[bot] c4924651e1 Bump phpDocumentor/.github/.github/workflows/static-analysis.yml
Bumps [phpDocumentor/.github/.github/workflows/static-analysis.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/static-analysis.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-10 11:29:32 +00:00
dependabot[bot] 9bc9646aae Bump phpDocumentor/.github/.github/workflows/continuous-integration.yml
Bumps [phpDocumentor/.github/.github/workflows/continuous-integration.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/continuous-integration.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-10 11:29:30 +00:00
dependabot[bot] 6c18eb884e Bump phpDocumentor/.github/.github/workflows/coding-standards.yml
Bumps [phpDocumentor/.github/.github/workflows/coding-standards.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/coding-standards.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-10 11:29:29 +00:00
dependabot[bot] 02e67b3545 Bump phpDocumentor/.github/.github/workflows/dependency-analysis.yml
Bumps [phpDocumentor/.github/.github/workflows/dependency-analysis.yml](https://github.com/phpdocumentor/.github) from 0.8 to 0.9.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.8...v0.9)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github/.github/workflows/dependency-analysis.yml
  dependency-version: '0.9'
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2025-11-10 11:29:27 +00:00
Jaapio 4277f906ba Fix code style issue 2025-11-07 16:00:13 +01:00
Jaap van Otterdijk 94f8051919 Merge pull request #414 from W0rma/reflection-set-accessible
Do not call Reflection*::setAccessible() in PHP >= 8.1
2025-08-01 21:43:32 +02:00
Worma a508a8b1de setAccessible() does not have any effect as of PHP 8.1 2025-08-01 06:16:17 +02:00
Jaap van Otterdijk 65a4d3e9dd Merge pull request #410 from DannyvdSluijs/patch-1
Fix workflow badge, tweak stable and unstable badges
2025-04-21 09:16:29 +02:00
Danny van der Sluijs 9cd3a32603 Fix workflow badge, tweak stable and unstable badges 2025-04-18 11:00:37 +02:00
Jaap van Otterdijk 92dde6a591 Merge pull request #409 from phpDocumentor/enable-integration-tests
Fix newline detection on descriptions
2025-04-13 21:20:35 +02:00
Jaapio d1c6c03eaa Fix issue with tag description end detection. 2025-04-13 21:16:25 +02:00
Jaapio e2ad295cd6 Enable running integration tests in pipelines 2025-04-13 13:04:50 +02:00
Jaapio a549656c45 Remove bc checker 2025-04-13 12:57:36 +02:00
Jaap van Otterdijk 2a6c077aa5 Merge pull request #395 from phpDocumentor/dependabot/composer/doctrine/deprecations-1.1.4
Bump doctrine/deprecations from 1.1.3 to 1.1.4
2025-02-18 12:02:15 +01:00
dependabot[bot] 77e1c12eba Bump doctrine/deprecations from 1.1.3 to 1.1.4
Bumps [doctrine/deprecations](https://github.com/doctrine/deprecations) from 1.1.3 to 1.1.4.
- [Release notes](https://github.com/doctrine/deprecations/releases)
- [Commits](https://github.com/doctrine/deprecations/compare/1.1.3...1.1.4)

---
updated-dependencies:
- dependency-name: doctrine/deprecations
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-12-09 10:48:45 +00:00
Jaap van Otterdijk e5e784149a Merge pull request #394 from phpDocumentor/bugfix/phpstan-parser-2.0
Fix compatibility issue with phpstan 2.0 parser
2024-12-07 10:39:29 +01:00
Jaapio d46c3297fb Fix compatibility issue with phpstan 2.0 parser
The phpstan 2.0 release contains a fix which resolves the existing bug
in the old parser that didn't take the whole description when it was
multiline. Now the workaround is disabled when using phpstan parser v2

Fixes #393
2024-12-07 10:35:23 +01:00
Jaap van Otterdijk f3558a4c23 Merge pull request #385 from phpDocumentor/dependabot/composer/phpstan/phpstan-1.12.8
Bump phpstan/phpstan from 1.12.7 to 1.12.8
2024-11-12 12:25:25 +01:00
Jaap van Otterdijk 6a29e605ef Merge pull request #387 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.10.0
Bump phpdocumentor/type-resolver from 1.9.0 to 1.10.0
2024-11-12 12:25:00 +01:00
Jaapio d0e946cb14 Fix code style 2024-11-12 12:22:19 +01:00
Jaap van Otterdijk 5763b5b3f4 Merge pull request #386 from xabbuh/phpstan-phpdoc-parser-2
add support for phpstan/phpdoc-parser 2
2024-11-12 12:21:26 +01:00
dependabot[bot] 2f98b1ff32 Bump phpdocumentor/type-resolver from 1.9.0 to 1.10.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.9.0 to 1.10.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.9.0...1.10.0)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-11-11 10:54:17 +00:00
Christian Flothmann 2a8b28d42a add support for phpstan/phpdoc-parser 2 2024-11-10 22:44:37 +01:00
dependabot[bot] 234e9df908 Bump phpstan/phpstan from 1.12.7 to 1.12.8
Bumps [phpstan/phpstan](https://github.com/phpstan/phpstan) from 1.12.7 to 1.12.8.
- [Release notes](https://github.com/phpstan/phpstan/releases)
- [Changelog](https://github.com/phpstan/phpstan/blob/2.0.x/CHANGELOG.md)
- [Commits](https://github.com/phpstan/phpstan/compare/1.12.7...1.12.8)

---
updated-dependencies:
- dependency-name: phpstan/phpstan
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-11-07 10:12:01 +00:00
Jaapio 0c70d2c566 Resolve notice on undefined index
fixes #384
2024-11-06 12:58:54 +01:00
Jaapio 54e10d44fc Add tests for new tags 2024-11-04 22:26:31 +01:00
Jaap van Otterdijk fcb5c3df23 Merge pull request #377 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.9.0
Bump phpdocumentor/type-resolver from 1.8.2 to 1.9.0
2024-11-04 21:31:31 +01:00
dependabot[bot] 67d6486abf Bump phpdocumentor/type-resolver from 1.8.2 to 1.9.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.8.2 to 1.9.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.8.2...1.9.0)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-11-04 20:29:19 +00:00
Jaap van Otterdijk ede8f6df4d Merge pull request #383 from phpDocumentor/bump-phpstam
Bump phpstan
2024-11-04 21:20:13 +01:00
Jaapio 2911a4807e Bump phpstan
Fixes a number of phpstan issues.
2024-11-04 21:17:08 +01:00
Jaapio 6a5a3b7748 Fix codestyle issues 2024-11-04 21:01:58 +01:00
Jaap van Otterdijk 6fc32d3738 Merge pull request #374 from GautierDele/5.x
 method parameter default value rendering
2024-11-04 20:47:47 +01:00
Jaap van Otterdijk c29b3d1935 Merge pull request #378 from phpDocumentor/dependabot/composer/mockery/mockery-1.6.12
Bump mockery/mockery from 1.3.5 to 1.6.12
2024-11-04 19:26:28 +01:00
dependabot[bot] 57b5b4ba2f Bump mockery/mockery from 1.3.5 to 1.6.12
Bumps [mockery/mockery](https://github.com/mockery/mockery) from 1.3.5 to 1.6.12.
- [Release notes](https://github.com/mockery/mockery/releases)
- [Changelog](https://github.com/mockery/mockery/blob/1.6.x/CHANGELOG.md)
- [Commits](https://github.com/mockery/mockery/compare/1.3.5...1.6.12)

---
updated-dependencies:
- dependency-name: mockery/mockery
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-11-04 10:42:32 +00:00
Gautier DELEGLISE 1ed543b248 🚨 assure backward compatibility 2024-11-04 08:24:17 +01:00
Gautier DELEGLISE f26d445de6 ♻️ revert get default value to string 2024-11-03 23:28:27 +01:00
Jaap van Otterdijk 8ea94649e7 Merge pull request #375 from phpDocumentor/build-php84
Build on php 8.4
2024-11-03 21:56:20 +01:00
Jaapio f985773245 Apply more strict type checking 2024-11-03 21:54:10 +01:00
Jaapio db271d6f57 Switch to psalm phar 2024-11-03 21:31:28 +01:00
Jaapio d5ffce6dee Build on php 8.4 2024-11-03 21:20:59 +01:00
Gautier DELEGLISE 2b2242d323 🐛 default value from phpstan 2024-11-01 17:33:39 +01:00
Gautier DELEGLISE 54f9b11a4c Update MethodParameterFactory.php 2024-10-31 10:05:00 +01:00
Gautier DELEGLISE 6a623a4829 🚸 code review 2024-10-30 21:49:01 +01:00
Gautier DELEGLISE 93cfc743bd 💚 removed unecessary imports 2024-10-28 10:30:40 +01:00
Gautier DELEGLISE 992c829bad ♻️ cover more default value cases 2024-10-28 10:28:22 +01:00
Gautier DELEGLISE 456d2b0be2 🐛 left side of ?? is not nullable 2024-10-27 12:20:56 +01:00
Gautier DELEGLISE 442a3d1dc8 ♻️ variable might not be defined 2024-10-27 12:17:33 +01:00
Gautier DELEGLISE fde2b5916d method parameter default value rendering 2024-10-26 23:49:53 +02:00
Jaapio 60741fe387 Fix unittests 2024-08-14 22:00:37 +02:00
Jaapio 3f5534f776 Remove abstract factory 2024-08-14 21:57:29 +02:00
Jaapio 06e5db2279 Fix code style issues 2024-08-14 21:52:41 +02:00
Jaap van Otterdijk bd5b5a8c5d Merge pull request #373 from ahjdev/5.x
Add new tags
2024-08-14 21:28:18 +02:00
AhJ 47fea84af1 Add description 2024-07-27 18:07:00 +03:30
AhJ f17d98425c Seprate template-* tags 2024-07-27 18:06:52 +03:30
AhJ f93a6b70aa Register tags 2024-07-24 12:11:24 +03:30
AhJ cca538efed Add TemplateCovariant tag 2024-07-24 12:11:07 +03:30
AhJ 19b5535d39 Clean up 2024-07-24 12:10:58 +03:30
AhJ 3acbe24b17 Add Implements tags 2024-07-24 12:10:38 +03:30
AhJ f387e8faa9 Add Extends tags 2024-07-24 12:10:17 +03:30
AhJ a46da81e77 Add Template tag 2024-07-24 12:09:41 +03:30
AhJ 6908c99a87 Add mixin tag 2024-07-23 18:14:49 +03:30
AhJ a979495847 add doc 2024-07-16 21:25:04 +03:30
AhJ bbb6a02b91 Add implements 2024-07-16 21:19:04 +03:30
Jaap van Otterdijk aa53f8d437 Merge pull request #371 from szepeviktor/typos
Fix typos
2024-05-21 08:14:15 +02:00
Viktor Szépe ab86695010 Fix typos 2024-05-21 06:10:59 +00:00
Jaap van Otterdijk 65a1ca18a3 Merge pull request #368 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github-0.7
Bump phpDocumentor/.github from 0.6 to 0.7
2024-05-21 08:10:23 +02:00
Jaap van Otterdijk 9d07b3f7fd Merge pull request #370 from phpDocumentor/retry-parser-docblocs
Fix docblock tag descriptions
2024-05-21 07:55:05 +02:00
Jaapio 8c422ab43b Fix docblock tag descriptions
Newlines and whitespaces were not handled as before. This caused
issues for some users because our indent-recuction was broken.
The cause seems to be an upstream issue in phpstan parser which
is not resolved yet. But this work around post processing the tokens
helps us to make it work as before.
2024-05-21 07:50:53 +02:00
dependabot[bot] 7ed4f46ada Bump phpDocumentor/.github from 0.6 to 0.7
Bumps [phpDocumentor/.github](https://github.com/phpdocumentor/.github) from 0.6 to 0.7.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.6...v0.7)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-05-13 10:57:32 +00:00
Jaap van Otterdijk 88a07d2628 Merge pull request #367 from phpDocumentor/fix/description-regression
Bugfix: resolve issue with multiline descriptions
2024-05-08 20:52:15 +02:00
Jaapio 518be131c0 Bugfix: resolve issue with multiline descriptions
The phpstan parser is not consuming the full description when parsing
docblocks with a more complex description. For them it's mostlikely not an
issue as phpstan doesn't use the descriptions. But it will also parse
the descriptions into unexpected tags. This could be an advantage but is
not according to the phpdoc spec.

Our own tokenizer is already tokenizing the docblocks into the correct parts.
So all we needed to do is assume all remaining tokens in the phpstan ast belong
to the description. From there our own code is able to handle this as before in
v5.3.

fixes #365
2024-05-08 20:49:40 +02:00
Jaap van Otterdijk 2f7b34c2ee Merge pull request #366 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github-0.6
Bump phpDocumentor/.github from 0.5.0 to 0.6
2024-05-07 07:11:38 +02:00
dependabot[bot] a3fc14103f Bump phpDocumentor/.github from 0.5.0 to 0.6
Bumps [phpDocumentor/.github](https://github.com/phpdocumentor/.github) from 0.5.0 to 0.6.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.5.0...v0.6)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-04-15 10:33:49 +00:00
Jaap van Otterdijk 298d2febfe Merge pull request #364 from phpDocumentor/fix/catch-invalid-type-creation
Added test for regression on invalid types
2024-04-09 23:13:58 +02:00
Jaapio 64e172d8ae Added test for regression on invalid types 2024-04-09 23:09:05 +02:00
Jaapio 08acd34f7e Add test for constant references. 2024-04-08 22:15:57 +02:00
Jaap van Otterdijk 67a55cc31d Merge pull request #363 from phpDocumentor/fix/malformed-type-definitions
Be more strict about type definitions on param
2024-04-08 21:44:59 +02:00
Jaapio edd5f67143 Be more strict about type definitions on param
Throw on invalid type definitions and unexpected type definitions.
Not all types resolved by phpstan's parser are valid for docblocks,
they might in a more complex type system but I do not see how these
types would ever apply to param tags.
2024-04-08 21:38:01 +02:00
Jaapio f359e4f8ef Fix code style 2024-03-20 22:40:18 +01:00
Jaapio 7b2f618fe1 Add test for string value params
shows the correct behavior of #348

fixes #348
2024-03-20 22:16:52 +01:00
Jaap van Otterdijk c9b9e93018 Merge pull request #360 from phpDocumentor/fix/typeless_param
Add typeless parameter support.
2024-03-20 22:15:57 +01:00
Jaapio d3cbc396a9 Add extra deprecation 2024-03-20 22:07:56 +01:00
Jaapio fc9a2339f2 Implement fallback option for params without variable 2024-03-20 21:57:07 +01:00
Jaapio 98566f2504 Add typeless parameter support. 2024-03-12 22:49:26 +01:00
Jaapio 2b309a247d Fix ci script typo 2024-03-12 22:45:15 +01:00
Jaap van Otterdijk eb008b75d8 Merge pull request #359 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github-0.5.0
Bump phpDocumentor/.github from 0.3.0 to 0.5.0
2024-03-12 22:41:56 +01:00
dependabot[bot] ab337bf6a5 Bump phpDocumentor/.github from 0.3.0 to 0.5.0
Bumps [phpDocumentor/.github](https://github.com/phpdocumentor/.github) from 0.3.0 to 0.5.0.
- [Release notes](https://github.com/phpdocumentor/.github/releases)
- [Commits](https://github.com/phpdocumentor/.github/compare/v0.3.0...v0.5.0)

---
updated-dependencies:
- dependency-name: phpDocumentor/.github
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2024-03-12 21:38:37 +00:00
Jaapio c6d49fc451 Fix code style and bump to php 7.4 2024-03-12 22:28:53 +01:00
Jaap van Otterdijk 1c6b5465fa Merge pull request #357 from AydinHassan/fix-description-formatting-with-escaping
Fix rendering a description when it contains escaped chars and no tags
2024-03-12 22:17:14 +01:00
Jaap van Otterdijk 0b48e261e0 Bump to stable type resolver 2024-01-26 21:33:24 +01:00
Jaap van Otterdijk c86c8d449b Merge pull request #356 from sergiy-petrov/sergiy-petrov-patch-1
Test against php 8.3
2023-10-13 08:34:03 +02:00
Aydin Hassan ae20798fde Fix rendering a description when it contains escaped characters and no tags 2023-10-11 14:57:53 +02:00
Serhii Petrov 1286851b07 Test against php 8.3 2023-10-04 17:06:07 +03:00
Jaap van Otterdijk 7b21721772 Merge pull request #350 from phpDocumentor/dependabot/github_actions/phpDocumentor/dot-github-0.3.0
Bump phpDocumentor/.github from 0.1.0 to 0.3.0
2023-03-12 11:50:44 +01:00
dependabot[bot] c341c1dbc2 Bump phpDocumentor/.github from 0.1.0 to 0.3.0
Bumps phpDocumentor/.github from 0.1.0 to 0.3.0.

---
updated-dependencies:
- dependency-name: phpDocumentor/.github
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2023-03-06 10:56:30 +00:00
Jaapio 566af9fb94 Bump type resolver 2022-11-19 21:28:46 +01:00
Jaapio 29e383a759 Fix issue with missing registered factory 2022-11-14 22:00:05 +01:00
Jaap van Otterdijk ec81b5479a Merge pull request #344 from williamdes/gitattributes-update
Update .gitattributes
2022-11-14 08:58:30 +01:00
William Desportes e2825e04af Update .gitattributes 2022-11-12 12:59:22 +01:00
Jaap van Otterdijk b5dc333089 Merge pull request #343 from phpDocumentor/poc-phpstan-integration
PhpStan based tag parsing
2022-11-11 15:54:50 +01:00
Jaapio 1f95f3b735 Codestyle fixes and static analysis 2022-11-11 14:24:45 +01:00
Jaapio 6a92bc3ce9 Remove type logic from this package 2022-11-11 12:30:14 +01:00
Jaapio d6e90a3238 Add callable parameter support 2022-11-04 15:43:05 +01:00
Jaapio 50bf16734e Add support for constant types.
phpstan supports contant definitions and expressions to
link to constants.
2022-11-04 11:21:53 +01:00
Jaapio 8d57d3da2d Add deprecation to getArguments 2022-10-28 22:43:02 +02:00
Jaapio 81553b535f Add default types to method tag arguments 2022-10-28 22:37:28 +02:00
Jaapio e4ac07bc40 Add method support 2022-10-28 22:25:08 +02:00
Jaapio cfe9845260 Add property support 2022-10-28 21:07:34 +02:00
Jaapio 1dd491c8ec Add return tag factory 2022-10-28 16:47:01 +02:00
Jaapio b12a33921b Add deprecations 2022-10-28 16:41:00 +02:00
Jaapio 25d696587f Cleanup and var implementation 2022-10-28 16:27:10 +02:00
Jaapio b66b6dc644 Fix some php8+ issues 2022-10-28 14:54:08 +02:00
Jaapio c6f6e2d523 Improve naming for tag factory 2022-10-28 14:39:55 +02:00
Jaapio ece4f5ab18 Introduce a Simple implementation of the TagFactory interface
Less complex interface to implement makes it easier to implement tag factories as they
are part of the new behavior of the StandardTagFactory.
2022-10-28 14:37:01 +02:00
Jaapio d6c050a533 WIP 2022-10-28 14:05:33 +02:00
Jaapio 7192e67cfa First POC steps 2022-10-14 15:26:54 +02:00
Jaap van Otterdijk 203354b3c0 Merge pull request #340 from phpDocumentor/modernize_ci
Upgrade ci to standardized pipeline
2022-08-27 12:55:55 +02:00
Jaapio 863ec23a9e Upgrade ci to standardized pipeline 2022-08-27 12:51:20 +02:00
Jaap van Otterdijk 407c40dcfb Merge pull request #338 from phpDocumentor/dependabot/composer/psalm/phar-4.24.0
Bump psalm/phar from 4.22.0 to 4.24.0
2022-07-27 22:03:43 +02:00
Jaap van Otterdijk 8d72b24f12 Merge pull request #336 from phpDocumentor/dependabot/composer/webmozart/assert-1.11.0
Bump webmozart/assert from 1.10.0 to 1.11.0
2022-07-27 22:03:25 +02:00
dependabot[bot] 43bc01edca Bump psalm/phar from 4.22.0 to 4.24.0
Bumps [psalm/phar](https://github.com/psalm/phar) from 4.22.0 to 4.24.0.
- [Release notes](https://github.com/psalm/phar/releases)
- [Commits](https://github.com/psalm/phar/compare/4.22.0...4.24.0)

---
updated-dependencies:
- dependency-name: psalm/phar
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2022-07-22 14:20:10 +00:00
dependabot[bot] a4764e401f Bump webmozart/assert from 1.10.0 to 1.11.0
Bumps [webmozart/assert](https://github.com/webmozarts/assert) from 1.10.0 to 1.11.0.
- [Release notes](https://github.com/webmozarts/assert/releases)
- [Changelog](https://github.com/webmozarts/assert/blob/master/CHANGELOG.md)
- [Commits](https://github.com/webmozarts/assert/compare/1.10.0...1.11.0)

---
updated-dependencies:
- dependency-name: webmozart/assert
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2022-07-22 14:20:08 +00:00
Jaap van Otterdijk 3032f88c16 Merge pull request #333 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.6.1
Bump phpdocumentor/type-resolver from 1.6.0 to 1.6.1
2022-07-22 16:19:31 +02:00
dependabot[bot] df5088c683 Bump phpdocumentor/type-resolver from 1.6.0 to 1.6.1
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.6.0 to 1.6.1.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.6.0...1.6.1)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2022-04-04 10:01:15 +00:00
Jaap van Otterdijk 9455bde915 Merge pull request #331 from phpDocumentor/dependabot/github_actions/actions/cache-3
Bump actions/cache from 2.1.7 to 3
2022-04-02 22:16:01 +02:00
Jaap van Otterdijk dd9861e924 Merge pull request #332 from villfa/feat/returns-reference
Support reference in method tag
2022-04-02 22:15:46 +02:00
Fabien Villepinte 29ed9ae60d Support reference in method tag 2022-03-31 13:22:11 +00:00
dependabot[bot] 8e19dd621a Bump actions/cache from 2.1.7 to 3
Bumps [actions/cache](https://github.com/actions/cache) from 2.1.7 to 3.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v2.1.7...v3)

---
updated-dependencies:
- dependency-name: actions/cache
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <[email protected]>
2022-03-29 20:10:23 +00:00
Jaapio 6baa6f8bd7 Remove scrutinizer 2022-03-29 22:08:34 +02:00
Jaapio 5e4ff887c6 Bump psalm 2022-03-29 22:06:36 +02:00
dependabot[bot] f8e84e03d1 Merge pull request #324 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.6.0 2022-03-29 19:20:41 +00:00
Jaap van Otterdijk 06325859d3 Merge pull request #329 from jrfnl/feature/ghactions-update-various-actions
GH Actions: version update for various predefined actions
2022-03-29 21:19:47 +02:00
jrfnl 13d8469422 GH Actions: version update for various predefined actions
A number of predefined actions have had major release, which warrant an update to the workflow(s).

These updates don't actually contain any changed functionality, they are mostly just a change of the Node version used by the action itself (from Node 14 to Node 16).

Refs:
* https://github.com/actions/checkout/releases
2022-03-05 19:50:40 +01:00
dependabot[bot] fda616c3a4 Bump phpdocumentor/type-resolver from 1.5.1 to 1.6.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.5.1 to 1.6.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.5.1...1.6.0)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2022-01-10 10:00:52 +00:00
Jaap van Otterdijk 21481a5c97 Merge pull request #311 from phpDocumentor/dependabot/github_actions/actions/cache-2.1.7
Bump actions/cache from 2.1.6 to 2.1.7
2021-12-27 23:36:43 +01:00
Jaap van Otterdijk 0535106ec9 Merge pull request #320 from villfa/ci/scrutinizer
Send code coverage to Scrutinizer
2021-12-27 23:36:19 +01:00
Jaap van Otterdijk 25cee6c463 Merge pull request #321 from jrfnl/feature/ghactions-update-composer-action
GH Actions: version update for `ramsey/composer-install`
2021-12-27 23:35:34 +01:00
jrfnl 92f06ed36f GH Actions: version update for ramsey/composer-install
The action used to install Composer packages and handle the caching has released a new major (and some follow-up patch releases), which means, the action reference needs to be updated to benefit from it.

Refs:
* https://github.com/ramsey/composer-install/releases/tag/2.0.0
* https://github.com/ramsey/composer-install/releases/tag/2.0.1
* https://github.com/ramsey/composer-install/releases/tag/2.0.2
2021-12-25 19:37:57 +01:00
Fabien Villepinte b9576df211 Send code coverage to Scrutinizer 2021-12-21 18:55:57 +00:00
Jaap van Otterdijk fd03393497 Merge pull request #319 from villfa/ci/dep-improvement
Test with multiple versions of the dependencies
2021-12-21 16:04:07 +01:00
Fabien Villepinte 33e88681c3 Test with multiple versions of the dependencies 2021-12-21 15:50:16 +01:00
Jaap van Otterdijk 647571f8e8 Merge pull request #318 from WinterSilence/patch-3
Optimize Description::render()
2021-12-20 08:08:37 +01:00
Jaap van Otterdijk 7769e9eb3a Merge pull request #317 from WinterSilence/patch-2
Fix PhpDoc in class Description
2021-12-20 08:07:01 +01:00
Anton e3d6818033 Optimize Description::render() 2021-12-18 21:35:58 +03:00
Anton 8e35c5f0db Update Description.php 2021-12-18 20:14:14 +03:00
dependabot[bot] b3680726d2 Bump actions/cache from 2.1.6 to 2.1.7
Bumps [actions/cache](https://github.com/actions/cache) from 2.1.6 to 2.1.7.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v2.1.6...v2.1.7)

---
updated-dependencies:
- dependency-name: actions/cache
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-11-29 10:00:59 +00:00
Jaap van Otterdijk 622548b623 Merge pull request #306 from kea/fix-example4
Remove deprecated StaticMethod and fix comment
2021-10-19 19:43:47 +02:00
Manuel Kea Baldassarri c8b2244018 Remove deprecated StaticMethod and fix comment 2021-10-16 09:24:17 +02:00
Jaap van Otterdijk 0005eb9eae Merge pull request #305 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.5.1
Bump phpdocumentor/type-resolver from 1.5.0 to 1.5.1
2021-10-05 22:58:53 +02:00
dependabot[bot] dac3933d9d Bump phpdocumentor/type-resolver from 1.5.0 to 1.5.1
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.5.0 to 1.5.1.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.5.0...1.5.1)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-10-04 10:01:15 +00:00
Jaap van Otterdijk 0f36fa483b Merge pull request #303 from jrfnl/feature/phpunit-update-config
PHPUnit: update configuration
2021-09-27 21:30:08 +02:00
jrfnl 670b3b54af PHPUnit: update configuration
PHPUnit just released version 9.5.10 and 8.5.21.

This contains a particular (IMO breaking) change:

> * PHPUnit no longer converts PHP deprecations to exceptions by default (configure `convertDeprecationsToExceptions="true"` to enable this)

Let's unpack this:

Previously (PHPUnit < 9.5.10/8.5.21), if PHPUnit would encounter a PHP native deprecation notice, it would:
1. Show a test which causes a deprecation notice to be thrown as **"errored"**,
2. Show the **first** deprecation notice it encountered and
3. PHPUnit would exit with a **non-0 exit code** (2), which will fail a CI build.

As of PHPUnit 9.5.10/8.5.21, if PHPUnit encounters a PHP native deprecation notice, it will no longer do so. Instead PHPUnit will:
1. Show a test which causes a PHP deprecation notice to be thrown as **"risky"**,
2. Show the **all** deprecation notices it encountered and
3. PHPUnit will exit with a **0 exit code**, which will show a CI build as passing.

This commit reverts PHPUnit to the previous behaviour by adding `convertDeprecationsToExceptions="true"` to the PHPUnit configuration.

Refs:
* https://github.com/sebastianbergmann/phpunit/blob/9.5/ChangeLog-8.5.md
* https://github.com/sebastianbergmann/phpunit/blob/9.5/ChangeLog-9.5.md
2021-09-25 18:47:01 +02:00
Jaap van Otterdijk adf7a90588 Merge pull request #302 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.5.0
Bump phpdocumentor/type-resolver from 1.4.0 to 1.5.0
2021-09-23 20:17:06 +02:00
dependabot[bot] 91a16428da Bump phpdocumentor/type-resolver from 1.4.0 to 1.5.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.4.0 to 1.5.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.4.0...1.5.0)

---
updated-dependencies:
- dependency-name: phpdocumentor/type-resolver
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-09-20 10:02:18 +00:00
Jaap van Otterdijk c512fd308b Merge pull request #300 from phpDocumentor/dependabot/composer/psalm/phar-4.10.0
Bump psalm/phar from 4.9.3 to 4.10.0
2021-09-17 15:49:47 +02:00
dependabot[bot] 68c9ee9a00 Bump psalm/phar from 4.9.3 to 4.10.0
Bumps [psalm/phar](https://github.com/psalm/phar) from 4.9.3 to 4.10.0.
- [Release notes](https://github.com/psalm/phar/releases)
- [Commits](https://github.com/psalm/phar/compare/4.9.3...4.10.0)

---
updated-dependencies:
- dependency-name: psalm/phar
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-09-17 13:43:15 +00:00
Jaap van Otterdijk 9ebbb531c1 Merge pull request #301 from phpDocumentor/php81_support
Run test on php 8.1
2021-09-17 15:42:31 +02:00
Jaapio bafd0edab0 Bump mocker to fix php 8.1 tests 2021-09-17 15:35:18 +02:00
Jaapio a01675497f Run test on php 8.1 2021-09-17 15:27:30 +02:00
Jaap van Otterdijk be3b495b92 Merge pull request #290 from jrfnl/ghactions-fail-on-failing-test
GH Actions: fail the build if a test run fails
2021-09-17 15:23:58 +02:00
Jaap van Otterdijk d708b18227 Merge pull request #299 from villfa/test/298
Tests: add a case to cover issue #298
2021-09-17 10:37:36 +02:00
Jaap van Otterdijk e4b1dd3f91 Merge pull request #296 from phpDocumentor/fix/287-line-endings
Improve line-endings for windows.
2021-09-17 08:30:37 +02:00
Fabien Villepinte 98e82e39fa Tests: add a case to cover issue #298 2021-09-05 18:57:50 +00:00
Fabien Villepinte 44e31d19a6 Fix undefined index 2021-09-05 12:40:50 +02:00
Jaapio 6fa60f9f08 Fix code style 2021-08-26 22:32:25 +02:00
Jaapio c5e702d299 Allow serializer to have a configurable line-ending 2021-08-26 22:31:30 +02:00
Jaapio bca4974b0b Make split platform independend 2021-08-26 22:31:30 +02:00
Jaap van Otterdijk c212334d39 Merge pull request #295 from phpDocumentor/dependabot/composer/psalm/phar-4.9.3
Bump psalm/phar from 4.9.2 to 4.9.3
2021-08-26 14:24:56 +02:00
dependabot[bot] 8e8592bda6 Bump psalm/phar from 4.9.2 to 4.9.3
Bumps [psalm/phar](https://github.com/psalm/phar) from 4.9.2 to 4.9.3.
- [Release notes](https://github.com/psalm/phar/releases)
- [Commits](https://github.com/psalm/phar/compare/4.9.2...4.9.3)

---
updated-dependencies:
- dependency-name: psalm/phar
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-08-16 10:01:07 +00:00
Jaap van Otterdijk c5ac781da3 Merge pull request #277 from phpDocumentor/dependabot/github_actions/actions/cache-2.1.6
Bump actions/cache from 2.1.4 to 2.1.6
2021-08-13 11:13:23 +02:00
Jaap van Otterdijk 79d2777813 Merge pull request #294 from phpDocumentor/dependabot/composer/psalm/phar-4.9.2
Bump psalm/phar from 4.8.1 to 4.9.2
2021-08-09 19:52:09 +02:00
dependabot[bot] 1f1f2f0414 Bump psalm/phar from 4.8.1 to 4.9.2
Bumps [psalm/phar](https://github.com/psalm/phar) from 4.8.1 to 4.9.2.
- [Release notes](https://github.com/psalm/phar/releases)
- [Commits](https://github.com/psalm/phar/compare/4.8.1...4.9.2)

---
updated-dependencies:
- dependency-name: psalm/phar
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <[email protected]>
2021-08-09 10:00:47 +00:00
jrfnl 63aa02024c GH Actions: fail the build if a test run fails
The way things were set up now in the `phpunit` job, no matter whether tests passed or failed, the workflow would always continue.

I suspect this may have been set-up this way to make sure that all variations of test runs will actually be run ?
The downside is that, while you will see a  for the individual build in the workflow summary, the workflow will not be marked as failed, nor will the individual test builds be marked as failed.

If we look back at the last time the workflow was run completely, this can be seen in the annotations below the summary, which show that the Windows test runs all failed.
https://github.com/phpDocumentor/ReflectionDocBlock/actions/runs/370378454

I'm proposing to change this now by:
* Removing the `continue-on-error` for the test run.
* Adding the `fail-fast` key and setting it to `false`.
    By default this key is set to `true`, which means that if any individual build within the job fails, all other builds within the job will be cancelled.
    By setting it to `false`, all builds in the matrix will still be run, but if any of them fail, the workflow will be marked as "failed".
2021-08-08 22:30:14 +02:00
dependabot[bot] e5d5fb1aa2 Bump actions/cache from 2.1.4 to 2.1.6
Bumps [actions/cache](https://github.com/actions/cache) from 2.1.4 to 2.1.6.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v2.1.4...v2.1.6)

Signed-off-by: dependabot[bot] <[email protected]>
2021-08-08 20:16:22 +00:00
Jaap van Otterdijk ece0c41d6d Merge pull request #270 from phpDocumentor/dependabot/composer/webmozart/assert-1.10.0
Bump webmozart/assert from 1.9.1 to 1.10.0
2021-08-08 22:15:47 +02:00
Jaap van Otterdijk 8d73b8d29c Merge pull request #293 from jrfnl/feature/phpcs-fix-ruleset
PHPCS ruleset: remove an outdated exclusion
2021-08-08 22:09:39 +02:00
Jaap van Otterdijk 6698bfb1da Merge pull request #292 from jrfnl/feature/phive-upgrade-phpunit
Phive: upgrade used version of PHPUnit
2021-08-08 22:09:26 +02:00
jrfnl 839c177147 PHPCS ruleset: remove an outdated exclusion
The `SlevomatCodingStandard.Classes.UnusedPrivateElements` sniff has been removed from Slevomat.
2021-08-08 21:59:12 +02:00
jrfnl 6215ff6630 Phive: upgrade used version of PHPUnit 2021-08-08 21:53:50 +02:00
dependabot[bot] a254f61d62 Bump webmozart/assert from 1.9.1 to 1.10.0
Bumps [webmozart/assert](https://github.com/webmozart/assert) from 1.9.1 to 1.10.0.
- [Release notes](https://github.com/webmozart/assert/releases)
- [Changelog](https://github.com/webmozarts/assert/blob/master/CHANGELOG.md)
- [Commits](https://github.com/webmozart/assert/compare/1.9.1...1.10.0)

Signed-off-by: dependabot[bot] <[email protected]>
2021-08-08 19:33:57 +00:00
Jaapio ffff80c1a6 Resolve psalm return type
The original php method preg_split might return `string[][]` in some
situations, however this should never be the case for this library. By
adding an extra assert, we should be more safe.
2021-08-08 21:32:57 +02:00
jrfnl aa1efc030b CS: no whitespace before return type colon 2021-08-08 21:32:57 +02:00
jrfnl c269e1b26e Psalm: remove suppression of return type issue
... and fix it instead.
2021-08-08 21:32:57 +02:00
jrfnl 93198fae49 Psalm: suppress notice about preg_split $flags
As discussed in the PR:
> > Argument 4 of preg_split expects 0|1|2|3|4|5|6|7, parent type int provided (see https://psalm.dev/193)
>
> I believe this issue is for the `phpDocumentor\Reflection\Utils` class and expects the `pregSplit()` method to apply input validation to the value received for `$flags` before passing it off to the PHP native `preg_split()` function.
>
> IMO that's taking things a little too far as PHP will handle this internally without errors.
> See: https://3v4l.org/NdDRK
2021-08-08 21:32:56 +02:00
jrfnl b7f9b17881 Psalm: suppress two notices
The current version of Psalm flags the following issues:
```
ERROR: InvalidReturnType - src\Utils.php:44:16 - The declared return type 'array<array-key, string>' for phpDocumentor\Reflection\Utils::pregSplit is incorrect, got 'list<list<int|string>|string>' (see https://psalm.dev/011)
     * @return string[] Returns an array containing substrings of subject split along boundaries matched by pattern

ERROR: InvalidReturnStatement - src\Utils.php:55:16 - The inferred type 'list<list<int|string>|string>' does not match the declared return type 'array<array-key, string>' for phpDocumentor\Reflection\Utils::pregSplit (see https://psalm.dev/128)
        return $parts;
```

I'm suggest ignoring this as `list` isn't an officially supported type.
2021-08-08 21:32:56 +02:00
jrfnl 7172d132a3 Tags/Return: remove redundant condition
Psalm flags this condition as redundant:
```
ERROR: RedundantCondition - src/DocBlock/Tags/Return_.php:62:48 - "" can never contain non-empty-lowercase-string (see https://psalm.dev/122)
        return $type . ($description !== '' ? ($type !== '' ? ' ' : '') . $description : '');
```

Based on the statement in the line above - `$type = $this->type ? '' . $this->type : 'mixed';` -, Psalm is correct and the `$type` variable can never be an empty string.
2021-08-08 21:32:56 +02:00
jrfnl f5118ce302 Tags::__toString(): remove redundant type casts
Psalm flags these type casts as redundant:
```
ERROR: RedundantCastGivenDocblockType - src/DocBlock/Tags/Author.php:80:23 - Redundant cast to string given docblock-provided type (see https://psalm.dev/263)
        $authorName = (string) $this->authorName;

ERROR: RedundantCastGivenDocblockType - src/DocBlock/Tags/Example.php:150:21 - Redundant cast to string given docblock-provided type (see https://psalm.dev/263)
        $filePath = (string) $this->filePath;

ERROR: RedundantCastGivenDocblockType - src/DocBlock/Tags/Link.php:74:17 - Redundant cast to string given docblock-provided type (see https://psalm.dev/263)
        $link = (string) $this->link;

ERROR: RedundantCastGivenDocblockType - src/DocBlock/Tags/Method.php:228:23 - Redundant cast to string given docblock-provided type (see https://psalm.dev/263)
        $methodName = (string) $this->methodName;
```

I have verified each and can confirm that these are redundant. They are probably a left-over from the time when the `__construct()` method in these classes did not yet have type declarations.
2021-08-08 21:32:55 +02:00
jrfnl 155efd647f Utils::pregSplit: limit is not nullable
Correctly flagged by Psalm:
```
ERROR: PossiblyNullArgument - src\Utils.php:50:53 - Argument 3 of preg_split cannot be null, possibly null value provided (see https://psalm.dev/078)
        $parts = php_preg_split($pattern, $subject, $limit, $flags);
```

The `$limit` argument of the PHP native `preg_split()` function is not nullable.

Ref: https://www.php.net/manual/en/function.preg-split
2021-08-08 21:32:50 +02:00
jrfnl 9ab603b069 Psalm: switch from Phive to Composer
This switches the installation method for Psalm from Phive to Composer, while still using a Phar file for running Psalm.

Includes:
* Removing Psalm from the Phive configuration.
* Adding Psalm to the Composer configuration. Includes upgrading from version `3.11.2` to version `4.8.1`.
* Adjusting the script used in the `Makefile`.
    👉 Please verify and test this as things work differently on different OS-es and this should work for you.
* Adjusting the GH Actions script to use the Composer installed version of Psalm.

Note: due to the committed `composer.lock` file, Psalm will not automatically upgrade when newer versions are available.

Refs:
* https://github.com/vimeo/psalm/releases
* https://github.com/psalm/phar/releases
2021-08-08 21:31:44 +02:00
Jaap van Otterdijk e45d003a09 Merge pull request #291 from jrfnl/feature/cs-update
CS update after upstream changes
2021-08-08 21:14:39 +02:00
jrfnl 19e97332e5 CS: miscellaneous other whitespace fixes 2021-08-08 19:41:03 +02:00
jrfnl 11315744bf CS: blank line between different use statement types 2021-08-08 19:41:03 +02:00
jrfnl a607236134 CS: no whitespace before return type colon 2021-08-08 19:41:03 +02:00
jrfnl 2a1aba8089 PHPCS ruleset: update ruleset for upstream changes
* Fix the name and description to prevent confusion between the project ruleset and the organisation ruleset.
* Set the minimum PHP version for the PHPCompatibility standard.
* Don't require property type declarations.
* Ensure special characters used as literals in an exclude pattern are escaped.
2021-08-08 19:41:03 +02:00
Jaap van Otterdijk dc7d72e47e Merge pull request #288 from jrfnl/feature/docblock-source-phpstan-fix
DocBlock/Tags/Source: remove redundant code
2021-08-06 11:57:03 +02:00
Jaap van Otterdijk 9381f67ecc Merge pull request #289 from jrfnl/feature/composer-fix-autoload-dev
Composer: fix `autoload-dev` directive
2021-08-06 11:34:27 +02:00
Jaap van Otterdijk 8c8deff92b Merge pull request #282 from jrfnl/feature/ghactions-switch-to-composer-cache-action
GH Actions: simplify Composer caching
2021-08-06 11:33:24 +02:00
Jaap van Otterdijk be1f0c122d Merge pull request #281 from jrfnl/feature/ghactions-allow-manual-triggering
GH Actions: allow for manually triggering a workflow
2021-08-06 11:31:46 +02:00
Jaap van Otterdijk 78dca37266 Merge pull request #285 from jrfnl/feature/tests-annotate-no-assertions
Tests: mark test without assertions as such
2021-08-01 22:21:35 +02:00
Jaap van Otterdijk d5fef100cc Merge pull request #286 from jrfnl/feature/tests-add-missing-coversnothing
Tests: fix missing `@covers` tag
2021-08-01 22:21:05 +02:00
Jaap van Otterdijk 88b67bd355 Merge pull request #283 from jrfnl/feature/docs-minor-fix
Docblock/Tags/Author: fix typo in method docblock
2021-08-01 22:19:28 +02:00
Jaap van Otterdijk ef02f64d74 Merge pull request #280 from jrfnl/feature/tests-fix-namespace
Tests: fix incorrect namespace
2021-08-01 22:17:39 +02:00
Jaap van Otterdijk e774a02926 Merge pull request #279 from jrfnl/feature/tests-fix-type-in-methodname
Tests: fix typo in test method name
2021-08-01 22:16:55 +02:00
Jaap van Otterdijk 384307b665 Merge pull request #269 from phpDocumentor/dependabot/composer/mockery/mockery-1.3.4
Bump mockery/mockery from 1.3.3 to 1.3.4
2021-08-01 21:39:08 +02:00
jrfnl 8dbbe4940d Composer: fix autoload-dev directive
This only allowed for the tests in the `tests/unit` directory, while there are also tests in the `tests/integration` directory.
2021-08-01 18:27:48 +02:00
jrfnl fcb8fe6588 DocBlock/Tags/Source: remove redundant code
PHPStan flags the code within the `Source::__toString()` method:
```
 ------ -------------------------------------------------------------------------------------------
  Line   DocBlock\Tags\Source.php
 ------ -------------------------------------------------------------------------------------------
  111    Result of || is always true.
  114    Result of || is always true.
  114    Result of || is always true.
 ------ -------------------------------------------------------------------------------------------
```

I have investigated this and can confirm that these flags are correct.

1. `$this->startingLine` is cast to an integer in the `__construct()` method (line 45) and subsequently cast to a string in `__toString()` (line 105).
    This means that it can only ever be a non-empty ("truthy") string or the string '0', so the `$startingLine || $startingLine === '0'` condition used in two places is redundant.
2. `$this->lineCount` is either an integer or `null` after the `__construct()` method (line 46).
    In the `__toString()` method, if the `lineCount` is an integer, it is effectively cast to a string by the concatenation with an empty string on line 107, while if the `lineCount` was `null`, it is turned into an empty string.
    By changing the concatenation from concatenating with an empty string to concatenating with a one-space string, we can remove the ternary in the `return` statement checking for `$lineCount` being empty.

The existing unit tests already cover this code and still pass after this change.
2021-08-01 17:56:47 +02:00
jrfnl 6eee464f8d Tests: fix missing @covers tag
... or rather add the missing `@coversNothing` as this is an integration test.

This prevents the test from being marked as "risky" due to the missing tag on PHPUnit 9.x:
```
There was 1 risky test:

1) phpDocumentor\Reflection\DocblockSeeTagResolvingTest::testResolvesSeeFQSENOfInlineTags
This test does not have a @covers annotation but is expected to have one
```
2021-08-01 14:17:11 +02:00
jrfnl 36f4124fa4 Tests: mark test without assertions as such
... to prevent it from being considered "risky" and being listed as "risky" below each test run.

```
There was 1 risky test:

1) phpDocumentor\Reflection\ModifyBackTraceSafeTest::testBackTraceModificationDoesNotImpactFunctionArguments
This test did not perform any assertions

/home/runner/work/ReflectionDocBlock/ReflectionDocBlock/tests/integration/ModifyBackTraceSafeTest.php:15
```
2021-08-01 14:16:50 +02:00
jrfnl d73732391f Docblock/Tags/Author: fix typo in method docblock 2021-08-01 05:16:32 +02:00
jrfnl 294709592f Tests: fix incorrect namespace 2021-08-01 04:33:44 +02:00
jrfnl 9c67b4c8b9 GH Actions: simplify Composer caching
... by using the `ramsey/composer-install` action.

Ref: https://github.com/marketplace/actions/install-composer-dependencies
2021-08-01 04:29:20 +02:00
jrfnl 8bc1e76abc GH Actions: allow for manually triggering a workflow
Triggering a workflow for a branch manually is not supported by default in GH Actions, but has to be explicitly allowed.

This is useful if, for instance, an external action script or composer dependency has broken.
Once a fix is available, failing builds for open PRs can be retriggered manually instead of having to be re-pushed to retrigger the workflow.

Ref: https://github.blog/changelog/2020-07-06-github-actions-manual-triggers-with-workflow_dispatch/
2021-08-01 04:28:58 +02:00
jrfnl 261f5b2a16 Tests: fix typo in test method name 2021-08-01 04:27:53 +02:00
Jaap van Otterdijk 8719cc12e2 Merge pull request #267 from phpDocumentor/dependabot/github_actions/actions/cache-v2.1.4
Bump actions/cache from v2 to v2.1.4
2021-04-23 11:50:58 +02:00
Jaap van Otterdijk 99e3fb891c Merge pull request #260 from voku/get_tags_with_type_by_name
Get tags with type by name
2021-04-23 11:50:05 +02:00
Jaap van Otterdijk f8d350d851 Merge pull request #262 from voku/more_tests
Only more tests
2021-03-07 12:12:25 +01:00
dependabot[bot] 56e4e57a1b Bump mockery/mockery from 1.3.3 to 1.3.4
Bumps [mockery/mockery](https://github.com/mockery/mockery) from 1.3.3 to 1.3.4.
- [Release notes](https://github.com/mockery/mockery/releases)
- [Changelog](https://github.com/mockery/mockery/blob/master/CHANGELOG.md)
- [Commits](https://github.com/mockery/mockery/compare/1.3.3...1.3.4)

Signed-off-by: dependabot[bot] <[email protected]>
2021-03-01 05:21:34 +00:00
dependabot[bot] ed0587db7f Bump actions/cache from v2 to v2.1.4
Bumps [actions/cache](https://github.com/actions/cache) from v2 to v2.1.4.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v2...26968a09c0ea4f3e233fdddbafd1166051a095f6)

Signed-off-by: dependabot[bot] <[email protected]>
2021-02-08 05:20:56 +00:00
Jaap van Otterdijk e3324ecbde Merge pull request #256 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.4.0
Bump phpdocumentor/type-resolver from 1.3.0 to 1.4.0
2020-11-18 15:27:38 +01:00
Lars Moelleken c2889e4c40 code styles fixes only 2020-10-24 10:34:38 +02:00
Lars Moelleken 0722b31031 "StandardTagFactory" -> add more tests 2020-10-24 10:33:49 +02:00
Lars Moelleken 2b6310620c "Uses" -> add more test only 2020-10-24 10:33:38 +02:00
Lars Moelleken e31c62da4c "See" -> add more test + simplify the regex 2020-10-24 10:33:28 +02:00
Lars Moelleken 5a2dd88e14 "Link" -> add some more tests 2020-10-24 10:33:17 +02:00
Lars Moelleken 3b4c4d1c2c "CoversTest" -> add only one more test 2020-10-24 10:33:08 +02:00
Lars Moelleken 591f5935c9 code styles fixes only 2020-10-24 10:29:01 +02:00
Lars Moelleken 8c3953ef86 "DocBlock" -> add "getTagsWithTypeByName()"
-> because I saw errors like this ```Call to undefined method phpDocumentor\Reflection\DocBlock\Tags\InvalidTag::getType()```

-> https://github.com/Roave/BetterReflection/blob/5b4d1c53768e2a3bc32ab348752663733fd70546/src/TypesFinder/FindReturnType.php#L53
2020-10-24 10:27:35 +02:00
dependabot[bot] 78e45517b9 Bump phpdocumentor/type-resolver from 1.3.0 to 1.4.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.3.0 to 1.4.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.3.0...1.4.0)

Signed-off-by: dependabot[bot] <[email protected]>
2020-09-21 05:40:47 +00:00
Jaap van Otterdijk 069a785b21 Merge pull request #254 from voku/fix_for_phpstorm_stubs
do not resolve types if it's not possible
2020-09-03 21:13:55 +02:00
Lars Moelleken 2ef4c3da53 add more unit tests and normalize the "__toString" methods
-> update the code coverage level
2020-09-03 02:54:11 +02:00
Lars Moelleken 5bb97a97c0 add more unit tests and normalize the "__toString" methods
-> fix code style v2
2020-09-03 02:51:17 +02:00
Lars Moelleken 4438ee7955 add more unit tests and normalize the "__toString" methods
-> fix code style + psalm reported errors
2020-09-03 02:38:39 +02:00
Lars Moelleken 4e6d7ecd03 add more unit tests and normalize the "__toString" methods v2 2020-09-03 02:06:24 +02:00
Lars Moelleken 7b7c22ddc3 Merge remote-tracking branch 'upstream/master' into fix_for_phpstorm_stubs
* upstream/master:
  Bump mockery
  Fix FQSEN resolving on see,covers,uses
  Improve test coverage
2020-09-03 00:41:27 +02:00
Lars Moelleken 3d8d7df9f1 clean-up code comments 2020-09-03 00:35:02 +02:00
Lars Moelleken 97863e0c44 add more unit tests and normalize the "__toString" methods 2020-09-03 00:33:09 +02:00
Jaapio f6075926e9 Bump mockery 2020-09-02 23:38:01 +02:00
Jaap van Otterdijk 86733dc09c Merge pull request #226 from phpDocumentor/fix-resolve-all-fqsen-formats
Fix FQSEN resolving on see,covers,uses
2020-09-02 23:14:11 +02:00
Lars Moelleken bbe0f54877 add more unit tests and fixed the output v2 2020-09-02 22:55:00 +02:00
Jaapio 73650dde91 Fix FQSEN resolving on see,covers,uses
The See, Covers and Use tags can reference also methods, properties and
constants. Which means that the FqsenResolver cannot handle those properly.
This patch fixes that issue.
2020-09-02 22:48:30 +02:00
Jaapio 08c0b366d7 Improve test coverage 2020-09-02 22:46:14 +02:00
Lars Moelleken be6ed8b0d8 add more unit tests and fixed the output 2020-09-02 22:23:55 +02:00
Lars Moelleken acf538a461 Param: do not resolve types if it's not possible (fix code style) 2020-09-01 19:42:29 +02:00
Lars Moelleken 2e6cecb9ef Param: do not resolve types if it's not possible
-> https://travis-ci.org/github/JetBrains/phpstorm-stubs/builds/723069982

-> https://github.com/JetBrains/phpstorm-stubs/pull/892
2020-09-01 17:52:33 +02:00
Jaap van Otterdijk 13d9a6bb0b Merge pull request #239 from Kasp42/patch-1
Update Link.php
2020-08-22 09:19:02 +02:00
dependabot[bot] 5ac2a85049 Merge pull request #252 from phpDocumentor/dependabot/composer/mockery/mockery-1.3.3 2020-08-22 07:18:24 +00:00
Jaap van Otterdijk 699b11ee4b Merge pull request #253 from voku/fix_issue_251
Param: fix phpdoc with reference hint
2020-08-22 08:59:18 +02:00
Lars Moelleken 3d38a9c3bb Param: fix phpdoc with reference hint (code style fixes v2) 2020-08-18 09:53:22 +02:00
Lars Moelleken b5f863d3da Param: fix phpdoc with reference hint (code style fixes) 2020-08-18 09:48:21 +02:00
Lars Moelleken 443d86e18e Param: fix phpdoc with reference hint
fix issue #251
2020-08-17 23:44:09 +02:00
dependabot[bot] 9281cf91b9 Bump mockery/mockery from 1.3.2 to 1.3.3
Bumps [mockery/mockery](https://github.com/mockery/mockery) from 1.3.2 to 1.3.3.
- [Release notes](https://github.com/mockery/mockery/releases)
- [Changelog](https://github.com/mockery/mockery/blob/1.3.3/CHANGELOG.md)
- [Commits](https://github.com/mockery/mockery/compare/1.3.2...1.3.3)

Signed-off-by: dependabot[bot] <[email protected]>
2020-08-17 06:18:41 +00:00
Jaap van Otterdijk f3ab30788f Merge pull request #247 from phpDocumentor/safe_preg_split
Introduce safe preg_split
2020-08-15 14:16:28 +02:00
Jaapio 690d9cd45f Introduce safe preg_split
Removes the need for extra assertions which makes the code
more readable, and reduces the overhead of an is_array check.
2020-08-15 14:06:55 +02:00
Jaap van Otterdijk d870572532 Merge pull request #250 from phpDocumentor/fix/modified-backtrace-arguments
Fix issue with modified backtrace
2020-08-15 13:14:08 +02:00
Jaapio 584a54ca0d Bump phpunit 2020-08-12 19:52:10 +02:00
Jaapio 6ff90eb7bd Fix issue with modified backtrace
php allows the backtrace arguments to be modified via the
backtrace. By using array_map we make sure that we do not overwrite
references.
2020-08-12 18:07:00 +02:00
Jaapio f0af3b7263 Add more tests 2020-08-12 15:27:12 +02:00
Jaapio 1ac416df3f Ensure docblock defaults 2020-07-21 10:16:41 +02:00
Jaap van Otterdijk 3170448f57 Merge pull request #246 from phpDocumentor/php72/phpunit8
update to phpunit 9.2
2020-07-20 22:05:34 +02:00
Jaapio a77432fbb0 update to phpunit 9.2
phpunit 9.2 is the latests version but not supported on php 7.2
we are supporting php 7.2 for now, so downgrade for that purpose
2020-07-20 21:59:04 +02:00
Jaapio 5316142b0f Install tools per step to prevent errors 2020-07-20 21:38:19 +02:00
Jaapio 2b7f96583d Enable php8 in build matrix 2020-07-20 21:27:58 +02:00
Jaapio 9781068ce1 Move away from phropecy since it is not php8 ready 2020-07-20 21:20:51 +02:00
Jaap van Otterdijk eb3320ef01 Merge pull request #244 from GrahamCampbell/patch-1
Fix PHP 8.0 support
2020-07-09 14:42:26 +02:00
Graham Campbell 44319e2691 Fixed PHP 8.0 builds 2020-07-09 09:38:20 +01:00
Jaap van Otterdijk 7c87da1725 Merge pull request #240 from DerManoMann/reflectionparameter-getclass-deprecated-php8
Use ReflectionParameter::getType() instead of getClass()
2020-07-07 16:44:20 +02:00
Martin Rademacher 321abc52ae Handle typehint value 'self' 2020-07-07 11:00:15 +12:00
Martin Rademacher 65a85616f4 Use ReflectionParameter::getType() instead of getClass()
`iReflectionParameter::getClass()` is deprecated as of PHP 8 and will
trigger a warning.
2020-07-06 17:20:21 +12:00
Jaapio 41f77e8697 Remove phpstan from phive 2020-07-03 08:45:43 +02:00
Jaapio cbe141db0f Update phpstan 2020-07-03 08:40:40 +02:00
Vladislav Kobzev 1be15702a5 Update Link.php 2020-07-01 16:10:10 +03:00
Jaapio 664187301b Downgrade mockery 2020-06-27 19:33:53 +02:00
Jaapio 70745c7dcb Bump dependencies 2020-06-27 17:54:35 +02:00
Jaapio da1c4e7d06 Remove unused dependency 2020-06-27 16:46:17 +02:00
Jaap van Otterdijk 04ad1dd646 Merge pull request #237 from phpDocumentor/php-8
Add php 8 to build matrix
2020-06-27 14:58:06 +02:00
Jaapio cfd5b88569 Allow this package on php8 2020-06-27 14:48:53 +02:00
Jaapio acd4c1fc9d Add php 8 to build matrix 2020-06-27 14:43:28 +02:00
Jaap van Otterdijk adacaaab2f Merge pull request #235 from phpDocumentor/dependabot/github_actions/phpDocumentor/phpstan-ga-0.12.9
Bump phpDocumentor/phpstan-ga from 0.12.3 to 0.12.9
2020-06-27 14:32:41 +02:00
Jaap van Otterdijk dcb2e76f35 Merge pull request #234 from phpDocumentor/dependabot/github_actions/actions/cache-v2
Bump actions/cache from v1 to v2
2020-06-27 14:30:53 +02:00
dependabot[bot] 275c80691b Bump phpDocumentor/phpstan-ga from 0.12.3 to 0.12.9
Bumps [phpDocumentor/phpstan-ga](https://github.com/phpDocumentor/phpstan-ga) from 0.12.3 to 0.12.9.
- [Release notes](https://github.com/phpDocumentor/phpstan-ga/releases)
- [Commits](https://github.com/phpDocumentor/phpstan-ga/compare/0.12.3...6c5df17f25d143e917106d8241f8ec033209cdde)

Signed-off-by: dependabot[bot] <[email protected]>
2020-06-27 12:21:29 +00:00
dependabot[bot] 31687bf357 Bump actions/cache from v1 to v2
Bumps [actions/cache](https://github.com/actions/cache) from v1 to v2.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v1...b8204782bbb5f872091ecc5eb9cb7d004e35b1fa)

Signed-off-by: dependabot[bot] <[email protected]>
2020-06-27 12:21:29 +00:00
Jaapio 2e17bb199a Add github actions to dependabot 2020-06-27 14:20:56 +02:00
Jaap van Otterdijk e3120da3fa Merge pull request #224 from phpDocumentor/dependabot/composer/doctrine/instantiator-1.3.1
Bump doctrine/instantiator from 1.3.0 to 1.3.1
2020-06-27 13:57:32 +02:00
Jaap van Otterdijk 9bdb16165f Merge pull request #232 from phpDocumentor/dependabot/composer/phpdocumentor/type-resolver-1.3.0
Bump phpdocumentor/type-resolver from 1.0.1 to 1.3.0
2020-06-27 13:57:03 +02:00
Jaap van Otterdijk 9323ba40c1 Merge pull request #231 from phpDocumentor/dependabot/composer/phpdocumentor/reflection-common-2.2.0
Bump phpdocumentor/reflection-common from 2.0.0 to 2.2.0
2020-06-27 13:56:39 +02:00
Jaap van Otterdijk b1d4733ab7 Merge pull request #228 from phpDocumentor/dependabot/add-v2-config-file
Update Dependabot config file
2020-06-27 13:56:00 +02:00
dependabot-preview[bot] 31fa427e86 Bump doctrine/instantiator from 1.3.0 to 1.3.1
Bumps [doctrine/instantiator](https://github.com/doctrine/instantiator) from 1.3.0 to 1.3.1.
- [Release notes](https://github.com/doctrine/instantiator/releases)
- [Commits](https://github.com/doctrine/instantiator/compare/1.3.0...1.3.1)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2020-06-27 11:37:42 +00:00
dependabot-preview[bot] 805f40f6fa Bump phpdocumentor/type-resolver from 1.0.1 to 1.3.0
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 1.0.1 to 1.3.0.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/1.0.1...1.3.0)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2020-06-27 11:35:15 +00:00
dependabot-preview[bot] 3db3b4d9d4 Bump phpdocumentor/reflection-common from 2.0.0 to 2.2.0
Bumps [phpdocumentor/reflection-common](https://github.com/phpDocumentor/ReflectionCommon) from 2.0.0 to 2.2.0.
- [Release notes](https://github.com/phpDocumentor/ReflectionCommon/releases)
- [Commits](https://github.com/phpDocumentor/ReflectionCommon/compare/2.0.0...2.2.0)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2020-06-27 11:33:57 +00:00
Jaap van Otterdijk 7854965c2c Merge pull request #225 from GrahamCampbell/patch-1
Removed unnecessary version constraint
2020-06-27 13:33:48 +02:00
Jaapio a93d44f1e1 Add psalm key 2020-06-27 13:25:20 +02:00
Jaapio 4d1a808f18 Bump qa tools 2020-06-27 13:19:36 +02:00
dependabot-preview[bot] beaae59675 Update Dependabot config file 2020-06-19 19:32:10 +00:00
Jaap van Otterdijk 790426f28b Merge pull request #227 from vladyslavstartsev/patch-1
remove (from publishing) files that are not needed for end user
2020-06-19 20:58:43 +02:00
vladyslavstartsev 61682ff0ff remove (from publishing) files that are not needed for end user 2020-06-19 01:57:56 +03:00
Jaapio 5892a510fe Fix phpstan workflow 2020-06-18 22:57:11 +02:00
Jaapio 01848b641d Use composer image to install dependencies 2020-06-18 22:50:07 +02:00
Graham Campbell 47691ae2be Removed unnecessary version constraint 2020-06-15 13:21:21 +01:00
Jaap van Otterdijk cd72d394ca Merge pull request #212 from orklah/static-fixes
change somes things for SA
2020-02-22 13:28:44 +01:00
Orklah 9724d359e9 change somes things for SA 2020-02-22 12:03:05 +01:00
Jaap van Otterdijk 8bc250e5d2 Merge pull request #214 from phpDocumentor/feature/improve-ci
Improve ci setup
2020-02-22 11:15:11 +01:00
Jaapio 98f8eeaa24 Improve ci setup 2020-02-22 11:08:00 +01:00
Jaap van Otterdijk 5463f8d32c Merge pull request #207 from orklah/static-analysis
More static analysis fixes
2020-02-20 21:42:36 +01:00
Orklah 8641f53768 fix CS 2020-02-20 21:30:57 +01:00
Orklah 43288974a5 small fixes 2020-02-20 21:26:56 +01:00
Jaap van Otterdijk 45e5409b3f Merge pull request #210 from TysonAndre/patch-1
Fix typo in .PHONY for Makefile
2020-02-20 20:45:11 +01:00
Tyson Andre 3c866bb5ff Fix typo in .PHONY for Makefile 2020-02-20 14:43:17 -05:00
dependabot-preview[bot] 011b369030 Bump webmozart/assert from 1.6.0 to 1.7.0
Bumps [webmozart/assert](https://github.com/webmozart/assert) from 1.6.0 to 1.7.0.
- [Release notes](https://github.com/webmozart/assert/releases)
- [Changelog](https://github.com/webmozart/assert/blob/master/CHANGELOG.md)
- [Commits](https://github.com/webmozart/assert/compare/1.6.0...1.7.0)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2020-02-17 17:48:35 +00:00
Jaap van Otterdijk edea3e8693 Merge pull request #206 from phpDocumentor/bc-check
Bc check
2020-02-12 21:05:04 +01:00
Jaapio 917b6648e6 CSFixes 2020-02-12 20:14:58 +01:00
Jaapio 50b2bc6670 Fetch tags 2020-02-12 20:01:06 +01:00
Jaap van Otterdijk b21eaf3a01 Merge pull request #201 from orklah/master
bump phpstan to master
2020-02-12 19:32:43 +01:00
Jaapio b73a2b7be0 Add bc check to ci 2020-02-12 19:30:27 +01:00
Jaapio 5b4b720bd1 Add bc check to ci 2020-02-12 19:29:34 +01:00
Jaap van Otterdijk 49a9955ef6 Merge pull request #205 from remicollet/issue-74
don't rely on 'args' in trace, not available in 7.4
2020-02-12 19:13:16 +01:00
Remi Collet e8384e45fa don't rely on 'args' in trace, not available in 7.4 2020-02-12 13:46:34 +01:00
Mike van Riel 50e77ace68 Change unit testing to match phpDocumentor itself 2020-02-12 08:18:08 +01:00
Andreas Prucha - Abexto 1070e666aa Make getter for bodyTemplate public in order to make conversion of existig Description to custom Description class easier (e.g. new MyDescriptionClass($origionalDescription->getBodyTemplate(), $origionalDescription->getTags();) 2020-02-12 07:52:22 +01:00
Daniel Rotter 51b773933d Make regex for method more performant to avoid catastrophic backtracking 2020-02-12 07:28:49 +01:00
Daniel Rotter 8727095d6b Add failing testcase for long method name 2020-02-12 07:28:49 +01:00
Orklah ada1b6be7f bump phpstan to master. Fixed ignored errors 2020-02-10 21:41:22 +01:00
Jaap van Otterdijk e2ce1d210a Merge pull request #202 from drupol/fix-for-php74
PHP 7.4 fix - Ensure the existence of the 'args' key.
2020-02-10 21:23:05 +01:00
Pol Dellaiera 91307e3009 Fix previous erroneous assignment. 2020-02-10 21:04:24 +01:00
Jaapio 1ef2c9d917 Build on push & pr 2020-02-10 19:44:24 +01:00
Pol Dellaiera 1c6203a9f7 PHP 7.4 fix - Create a temporary variable to prevent Fatal error. 2020-02-10 13:22:22 +01:00
Pol Dellaiera adcffd685b PHP 7.4 fix - Check if 'args' key exists, if not, use an empty array. 2020-02-10 11:52:42 +01:00
Pol Dellaiera e6166a8b40 PHP 7.4 fix - Ensure the existence of the 'args' key. 2020-02-10 11:19:17 +01:00
Jaapio a48807183a Add github action status badge 2020-02-09 10:16:15 +01:00
Jaapio a83a19f71b Fix code style 2020-02-09 10:13:47 +01:00
Jaapio 1e5bd86da1 Fix invalid void type default for arguments 2020-02-09 09:31:53 +01:00
Jaap van Otterdijk a8dc047f21 Merge pull request #200 from phpDocumentor/feature/improved-tag-parsing
Limit characters after tag name
2020-02-09 09:15:34 +01:00
Jaapio 9169749b9e Improve test descriptions 2020-02-09 09:11:55 +01:00
Jaapio 264bd1fff7 Handle tag specialization correctly 2020-02-09 09:05:22 +01:00
Jaapio ed7b7919e3 Limit characters after tag name
Previously we allowed all characters after a tag name which made
it a bit fuzzy how tags are handled. Psr-5 is more strict about
the characters that are allowed in tags and those that are part of
the body. A tag name can now be followed by `(`, <space> and `{` all
other characters are forbidden. The first character of the body is
not restricted anymore.

fixes #165
2020-02-09 08:52:29 +01:00
Jaapio 6a88d1ae42 use phpstan action 2020-02-05 21:17:02 +01:00
Jaapio da71602ae9 Fix issue on workflow 2020-02-02 20:24:25 +01:00
Jaapio 6239e0d184 Switch to phpdoc coding-standard 2020-02-02 11:33:17 +01:00
Jaapio 93919e334b Fix code style 2020-01-27 21:01:09 +01:00
Jaapio 31fd6db84f Return invalid tag when factory returned null 2020-01-25 15:52:34 +01:00
Jaapio cf16f630f2 Fix code style 2020-01-16 09:49:07 +01:00
Jaapio ce65c06bb6 Fix serialization issue of InvalidTag 2020-01-16 09:38:58 +01:00
Jaap van Otterdijk f256f0b49e Merge pull request #198 from phpDocumentor/fix/invalid-tag-usage-fix
Fix issue when processing invalid tags
2020-01-12 13:26:24 +01:00
Jaapio bb629f6469 Improvements to code 2020-01-12 13:19:45 +01:00
Jaapio 1b78639b8b Add testcase for invalid tag creation 2020-01-03 14:06:44 +01:00
Jaapio bdecc2d3bf Fix issue when processing invalid tags
When invalid tags are processed a null was returned causing all kind
of issues in the normal behavior of this libary. As a solution a generic tag
could be created. But that would just drop the error information in.
Therefore a new tag was introduced, `invalidTag` the tag is just like the
generic tag but does contain the error triggered during the creation of the
tag. Which might help applications like phpdocumentor to display validation issues.
2020-01-03 13:33:06 +01:00
dependabot-preview[bot] 43f90ab91c Bump mockery/mockery from 1.3.0 to 1.3.1
Bumps [mockery/mockery](https://github.com/mockery/mockery) from 1.3.0 to 1.3.1.
- [Release notes](https://github.com/mockery/mockery/releases)
- [Changelog](https://github.com/mockery/mockery/blob/master/CHANGELOG.md)
- [Commits](https://github.com/mockery/mockery/compare/1.3.0...1.3.1)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2019-12-30 09:40:11 +00:00
Mike van Riel c5a39003d5 Fixes #181: Example did not implement interface 2019-12-27 21:42:04 +01:00
Mike van Riel b668892da4 Fix tests and linting errors after merging in release 4.x 2019-12-27 21:38:28 +01:00
Mike van Riel 1a5d9a2dbc Add braces support to Property, Property-Read, Property-Write and Var 2019-12-27 21:07:05 +01:00
Mike van Riel bb19583948 Support braces in types for @param 2019-12-27 21:02:14 +01:00
Mike van Riel 506fd89d43 Move type extraction to base class and re-use in Throws 2019-12-27 20:59:58 +01:00
Mike van Riel 0a9b8ea383 Add extra tests to check for multibyte behaviour 2019-12-27 20:18:40 +01:00
Mike van Riel 19dd184a2b Support braces in types for @return
In this change, I have introduced a miniature automaton-light to parse
the type from the @return body. This will prevent issues with people
using generics and other unsupported forms of types.

This change does _not_ allow for the use of Generics or similar; the
TypeResolver will still fail to resolve this type. This will remove a
breaking issue in consuming applications where a runtime exception used
to be thrown.

Please note that this change is only for @return; other tags still need
to be done. This will resolve issue #186
2019-12-27 20:18:32 +01:00
Jaapio c19ab7ef57 Upgrade phive phpstan:0.12.2 2019-12-20 14:36:14 +01:00
Jaap van Otterdijk d9e1217896 Merge pull request #188 from othercorey/method-arguments
Fixed @method annotations with an empty argument list and description
2019-12-20 14:23:12 +01:00
Corey Taylor 97b796040a Fixed @method annotations with an empty argument list and description 2019-12-19 08:41:51 -06:00
dependabot-preview[bot] 549d235cf4 Bump phpdocumentor/type-resolver from 0.6.2 to 1.0.1
Bumps [phpdocumentor/type-resolver](https://github.com/phpDocumentor/TypeResolver) from 0.6.2 to 1.0.1.
- [Release notes](https://github.com/phpDocumentor/TypeResolver/releases)
- [Commits](https://github.com/phpDocumentor/TypeResolver/compare/0.6.2...1.0.1)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2019-12-17 20:36:15 +00:00
dependabot-preview[bot] 1aef412299 Bump mockery/mockery from 1.1.0 to 1.3.0
Bumps [mockery/mockery](https://github.com/mockery/mockery) from 1.1.0 to 1.3.0.
- [Release notes](https://github.com/mockery/mockery/releases)
- [Changelog](https://github.com/mockery/mockery/blob/master/CHANGELOG.md)
- [Commits](https://github.com/mockery/mockery/compare/1.1.0...1.3.0)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2019-12-13 15:12:00 +00:00
dependabot-preview[bot] 0461e3ca1a Bump doctrine/instantiator from 1.1.0 to 1.3.0
Bumps [doctrine/instantiator](https://github.com/doctrine/instantiator) from 1.1.0 to 1.3.0.
- [Release notes](https://github.com/doctrine/instantiator/releases)
- [Commits](https://github.com/doctrine/instantiator/compare/1.1.0...1.3.0)

Signed-off-by: dependabot-preview[bot] <[email protected]>
2019-12-13 15:02:41 +00:00
Jaapio 79fd4a9475 Allow dependabot automerge 2019-12-13 16:01:35 +01:00
Jaap van Otterdijk 03ddbe014b Merge pull request #179 from phpDocumentor/cleanup
Cleanup
2019-12-13 15:42:32 +01:00
Jaapio 043df2c565 remove bc check for now 2019-12-13 15:31:58 +01:00
Jaapio 0bbc74b119 Remove ci configs to switch to github actions 2019-12-11 09:32:27 +01:00
Jaapio fc2eb2355e Add phpdoc workflow 2019-12-11 09:18:05 +01:00
Jaapio d7d476a5da Bump minimal required php version 2019-12-11 09:13:46 +01:00
Jaapio c14c01875a Make static anlisys pass 2019-12-10 23:46:06 +01:00
Jaapio 09e086ecf1 Cleanup build files 2019-09-26 21:19:59 +02:00
Jaapio 73ea6784b3 Add workflow to ensure checks 2019-09-26 21:11:19 +02:00
Jaapio 50ec1362de Psalm fixes 2019-09-26 21:09:37 +02:00
Jaapio 19a1f3a91f Phpstan to max level 2019-09-20 16:52:17 +02:00
Jaapio aee984014b Apply new code style 2019-09-20 10:54:12 +02:00
Mike van Riel 8fcadfe5f8 No longer bubble tag exceptions to the top
When a tag has an invalid component to it it would cause a whole file to fail
to parse. Instead we should consider invalid tags a nuisance but not worth
breaking the whole parsing over.

In this change I have added a try..catch that will prevent invalid tags from
breaking the whole parsing process.
2019-06-15 22:45:01 +02:00
Jaap van Otterdijk 48351665a8 Merge pull request #167 from michbeck/master
Fix for generic tag description properly parsing 0
2019-04-30 20:01:57 +02:00
Michael Knappe 6907decc71 added test for generic tag to parse description with 0 as expected 2019-04-30 13:22:06 +02:00
Michael Knappe 095cf6d37a fixed generic tag to parse description with 0 as expected 2019-04-30 13:21:57 +02:00
Jaap van Otterdijk 90ae750874 Merge pull request #161 from andreybolonin/patch-1
add php 7.3 to travis
2018-10-30 09:13:41 +01:00
Andrey Bolonin 6929bd4881 add php 7.3 to travis 2018-10-30 02:05:21 +02:00
Chuck Burgess a29cd5c528 initialize line count to an int; 2018-06-20 09:34:23 -05:00
Chuck Burgess 329341ac93 Merge pull request #157 from ashnazg/ci
use ecs v3.x
2018-06-14 11:15:19 -05:00
Chuck Burgess d31c40a6a1 use ecs v3.x 2018-06-14 11:01:00 -05:00
Chuck Burgess ef73f5cfdb Merge pull request #156 from ashnazg/reflection-needs
bump to next type-resolver alpha
2018-06-14 07:47:29 -05:00
Chuck Burgess 26a37cf245 restore global phpunit 2018-06-14 07:43:12 -05:00
Chuck Burgess 688e9d1e54 update appveyor config format 2018-06-14 07:35:11 -05:00
Chuck Burgess 4b73412a9d bump to next type-resolver alpha 2018-06-14 07:34:33 -05:00
Jaap van Otterdijk 6537078c5e Merge pull request #154 from jakzal/patch-1
Update the branch alias for 5.x releases
2018-04-19 10:00:57 +02:00
Jakub Zalas 9e75264359 Update the branch alias for 5.x releases
It's time to update the branch alias since BC breaking changes were merged and the first 5.0.0-alpha1 release has been made.
2018-04-19 08:58:50 +01:00
Chuck Burgess 1826097368 bump reflection-common 2018-02-14 13:00:58 -06:00
Chuck Burgess 2de1b36556 bump php versions 2018-02-14 08:05:46 -06:00
Chuck Burgess 238565e7a8 limit global phpunit to v6 2018-02-14 08:02:37 -06:00
Chuck Burgess 3eb278bd0e type-resolver update 2018-02-14 07:53:04 -06:00
Chuck Burgess 6946f85e19 Merge pull request #152 from ashnazg/strict
Strict Updates
2018-01-31 14:23:19 -06:00
Chuck Burgess cc0998e471 add self return type; 2018-01-31 08:58:25 -06:00
Chuck Burgess ff287a453f remove unused imports; 2018-01-31 08:58:03 -06:00
Chuck Burgess 5ea3cbf8cf add missing typehints and return types; 2018-01-31 08:57:30 -06:00
Chuck Burgess cd3bee0c73 Merge pull request #151 from ashnazg/ci
CI updates
2018-01-31 07:16:30 -06:00
Chuck Burgess 00c87ba426 adjust appveyor for global phpunit 2018-01-30 13:29:10 -06:00
Chuck Burgess 9073dd28d0 quieter wget 2018-01-30 13:17:34 -06:00
Chuck Burgess a6069276fd bump deps to get library alphas 2018-01-30 13:00:44 -06:00
Chuck Burgess 1a799237e1 try using global phpunit 2018-01-30 12:48:00 -06:00
Chuck Burgess d9952bd114 initialize variables before include, so that var tag usage is normal 2018-01-29 14:03:51 -06:00
Chuck Burgess ffc8cc1f9c remove dupe checker 2018-01-29 14:03:51 -06:00
Chuck Burgess 746bf9762b use phive and phars for tools 2018-01-29 14:03:51 -06:00
Chuck Burgess 8323f1a50a no need for converalls cfg 2018-01-29 14:03:51 -06:00
Chuck Burgess 25ec30d936 Merge pull request #150 from Nyholm/patch-1
Use package name in link to packagist
2018-01-29 14:02:07 -06:00
Tobias Nyholm 168df99062 Use package name in link to packagist 2018-01-29 20:58:22 +01:00
Chuck Burgess 86868b9202 Merge pull request #146 from ashnazg/ci
CI updates
2018-01-12 13:30:38 -06:00
Chuck Burgess 4a1e4dec73 no coverage for phpunit here 2018-01-11 07:18:38 -06:00
Chuck Burgess 14416207a8 don't analyze phpstan 2018-01-11 07:18:31 -06:00
Chuck Burgess 36c15f4a83 use shields for badges 2018-01-11 07:18:12 -06:00
Jaap van Otterdijk 9ff23ace62 Merge pull request #145 from ashnazg/ci
update travis build; add appveyor
2018-01-09 21:25:16 +01:00
Chuck Burgess 264e58724e url typo 2018-01-09 14:20:11 -06:00
Chuck Burgess 4f81271c85 run coverage before lint 2018-01-09 12:58:19 -06:00
Chuck Burgess e6fb1cbc9b add scrunitizer 2018-01-09 12:25:08 -06:00
Chuck Burgess ff49ab6be7 see if install makes it persist into stages 2018-01-08 17:03:37 -06:00
Chuck Burgess 90a60e6406 put test stage back together 2018-01-08 17:03:21 -06:00
Chuck Burgess fe337a20d6 some steps belong together 2018-01-08 17:01:56 -06:00
Chuck Burgess 15a808b6a8 xdebug removal proves complicated 2018-01-08 16:28:20 -06:00
Chuck Burgess c4fcd74584 add more badges 2018-01-08 16:14:16 -06:00
Chuck Burgess 09f8c7c6b6 try disabling xdebug for test stage only 2018-01-08 15:23:40 -06:00
Chuck Burgess 99338f3687 no coverage needed in test stage 2018-01-08 15:12:29 -06:00
Chuck Burgess 74a79e1014 add coveralls 2018-01-08 15:02:42 -06:00
Chuck Burgess 43f7d784e7 use php section layout from travis docs; 2018-01-08 14:37:09 -06:00
Chuck Burgess 41266d5ef5 add coveralls 2018-01-08 14:36:40 -06:00
Chuck Burgess a7d3aca868 use matrix for allow_failures; add fast_finish; 2018-01-08 14:36:22 -06:00
Chuck Burgess f845cf6567 put lint stages together 2018-01-08 14:35:36 -06:00
Chuck Burgess cda86e1f17 VERSION not needed in this package build 2018-01-08 14:34:47 -06:00
Chuck Burgess 66e1fd3837 unstaged scripts default to 'test' stage; 2018-01-08 14:34:10 -06:00
Chuck Burgess 1d7fe61bc1 travis docs imply quotes necessary are here 2018-01-08 14:32:38 -06:00
Chuck Burgess bd3b8fe05a add badges 2018-01-08 13:08:32 -06:00
Chuck Burgess 751934cd9a expand gitignore 2018-01-08 12:09:54 -06:00
Chuck Burgess da5670bae5 missing colon 2018-01-08 07:14:21 -06:00
Chuck Burgess 09489084f8 target php not allowed in lint stage? 2018-01-08 07:09:15 -06:00
Chuck Burgess 355187b692 move ECS & phpstan into a stage 2018-01-08 07:06:44 -06:00
Jaap van Otterdijk 3bf31c9f4e Merge pull request #144 from ashnazg/bug-63
Ellipsis in summary
2018-01-07 21:52:59 +01:00
Chuck Burgess 17333cc096 update travis build; add appveyor 2018-01-07 09:19:13 -06:00
Chuck Burgess 7bd0e7e4a1 extra space 2018-01-07 09:09:21 -06:00
Chuck Burgess fb948e8a52 regex fix for ellipsis in summary text; 2018-01-07 08:51:10 -06:00
Chuck Burgess 2f482c78b0 add tests for bug #63; 2018-01-07 08:50:54 -06:00
Jaap van Otterdijk c8a91684d6 Merge pull request #143 from TomasVotruba/ecs-fix
EasyCodingStandard - config path fixes + apply coding style
2018-01-03 09:19:52 +01:00
TomasVotruba d613cfc6ea rebuild composer.lock 2018-01-02 13:42:57 +01:00
TomasVotruba a44d973f3d composer: drop ecs 2018-01-02 13:42:26 +01:00
TomasVotruba 1c8f795c0e apply coding standard to code 2018-01-02 13:40:57 +01:00
TomasVotruba 89a0935960 travis: drop tests from phsptan, too many errors 2018-01-02 13:40:42 +01:00
TomasVotruba 84bd0918ef ecs - fix config paths 2018-01-02 13:39:56 +01:00
TomasVotruba 67d8d8eca5 travis: split PHPSTAN and ECS runs 2018-01-02 13:38:48 +01:00
TomasVotruba 803a9a5b80 composer: require ecs locally 2018-01-02 13:33:03 +01:00
Jaap van Otterdijk 996d0fb0e5 Merge pull request #142 from carusogabriel/2018
Welcome 2018 🎉
2018-01-02 08:30:15 +01:00
Gabriel Caruso a1e6160b99 Welcome 2018 🎉 2018-01-02 04:52:36 -02:00
Jaapio 4595df959d bump type resolver 2017-12-28 22:17:47 +01:00
Gabriel Caruso 4ea190884d Use assertCount (#140) 2017-12-07 21:29:55 +01:00
Tomáš Votruba bab88701ea Add PHPStan and bump to max level (#139)
* composer: put require- together

* add phpstan

* add phpstan to travis

* phpstan fixes

* phpstan fixes

* phpstan fixes

* drop null defaults since every property is null by default

* DescriptionFactory: fix parse nullable type

* travis: add phpstan max

* travis: fix phpstan config
2017-12-02 19:12:29 +01:00
TomasVotruba c19b4d170c [cs] remove value-less docblocks 2017-11-30 10:27:01 +01:00
TomasVotruba c664d2866d fix cs 2017-11-30 10:27:01 +01:00
TomasVotruba 7d2174e8f6 use ::class over string 2017-11-30 10:27:01 +01:00
TomasVotruba f8d4fda4f3 fix cs 2017-11-30 10:27:01 +01:00
TomasVotruba e9e35284d9 use PHPUnit 6.0 syntax for tests 2017-11-30 10:27:01 +01:00
TomasVotruba 5282c2e9a8 return test code back 2017-11-30 10:27:01 +01:00
TomasVotruba 51122cfa1d improve comment 2017-11-30 10:27:01 +01:00
TomasVotruba 082c811880 remove unused docblocks 2017-11-30 10:27:01 +01:00
TomasVotruba 4a9675841b add PHP 7.1 typehints 2017-11-30 10:27:01 +01:00
TomasVotruba f9d1a0c177 travis + composer: bump to PHP 7.1 2017-11-30 10:27:01 +01:00
TomasVotruba 0bac84ee68 remove unused docblocks 2017-11-30 10:27:01 +01:00
TomasVotruba 154c85b680 remove unused namespaces 2017-11-30 10:27:01 +01:00
TomasVotruba b2e816c8ad fix tests 2017-11-30 10:27:01 +01:00
TomasVotruba 5e1bad3628 drop asserts where not needed 2017-11-30 10:27:01 +01:00
TomasVotruba 193731a153 remove tests and validation that are now covered by typehints 2017-11-30 10:27:01 +01:00
TomasVotruba 76b771c23e examples: apply typehints 2017-11-30 10:27:01 +01:00
TomasVotruba 91c067abe5 update composer.lock 2017-11-30 10:27:01 +01:00
TomasVotruba a1d8751ad6 tests: add strict_types and typehints, remove tests that are now covered by typehints 2017-11-30 10:27:01 +01:00
TomasVotruba d874c4d14a add strict_types and typehints 2017-11-30 10:27:01 +01:00
TomasVotruba 94fd000123 fix cs 2017-11-30 08:14:17 +01:00
TomasVotruba 763f26e8db fix extra space after tag removal 2017-11-30 08:14:17 +01:00
TomasVotruba bdcc0cff11 Serializer - add test for tag removal extra spaces 2017-11-30 08:14:17 +01:00
Tomáš Votruba 66465776cf Example: add missing typehtins
This package actually fails on checking itself here
2017-11-27 18:38:31 +01:00
TomasVotruba 1119a97659 drop unused phpmd.xml 2017-11-15 20:01:54 +01:00
TomasVotruba 03f8b85625 use coveralls over scrutinizer 2017-11-15 20:01:54 +01:00
Gabriel Caruso 7524aba21f Fix tests 2017-11-15 08:29:42 +01:00
Gabriel Caruso fd1a734d29 Remove composer.lock, and update to PHPUnit 6 and Mockery 1 2017-11-15 08:29:42 +01:00
Gabriel Caruso c006d4a2d5 Use PHPUnit\Framework\TestCase instead of PHPUnit_Framework_TestCase 2017-11-15 08:29:42 +01:00
TomasVotruba 03b7048a61 README: improve install and examples 2017-11-12 21:24:40 +01:00
TomasVotruba 8959be6da0 gitignore: add temp 2017-11-12 21:23:54 +01:00
TomasVotruba 0ded2070d1 travis: run cs just once 2017-11-12 21:23:54 +01:00
TomasVotruba 5ff9ca38c5 [cs] finalize, spaces, concat and strict comparison 2017-11-12 21:23:54 +01:00
TomasVotruba 833126e6a3 [cs] ignore irelevant errors 2017-11-12 21:23:54 +01:00
TomasVotruba a872e515bb [cs] add and apply psr2 2017-11-12 21:23:54 +01:00
TomasVotruba 0294ce9b70 travis: add tests to cs check 2017-11-12 21:23:54 +01:00
TomasVotruba 44c0ac7d5f [cs] remove unused imports, short array and order imports on tests 2017-11-12 21:23:54 +01:00
TomasVotruba 6e5fc0c312 [cs] ignore temp code 2017-11-12 21:23:54 +01:00
TomasVotruba 771a21db91 [cs] use short arrays, order imports 2017-11-12 21:23:54 +01:00
TomasVotruba 87c6ecc5f4 init coding style check 2017-11-12 21:23:54 +01:00
TomasVotruba e223aa704a travis: add PHP 7.2 2017-11-12 21:23:54 +01:00
TomasVotruba dad79320b3 fix cs 2017-11-10 23:53:51 +01:00
TomasVotruba a69e7c5103 travis: drop unused commands 2017-11-10 23:53:51 +01:00
TomasVotruba c9c580e482 DocBlock: move public method up 2017-11-10 23:53:51 +01:00
TomasVotruba 0cb4b04fa6 add test for removeTag() 2017-11-10 23:53:51 +01:00
TomasVotruba 474fd9e29a add test for removeTag() 2017-11-10 23:53:51 +01:00
Tomáš Votruba c62f4592a0 DocBlock: add removeTag() method 2017-11-10 23:53:51 +01:00
Jaapio 14f9edf1ae Switch to phpdocumentor/reflection-common stable 2017-09-11 20:06:11 +02:00
Jaapio c5545d1519 Adds sort to order expected keys
Without this sort the order of argument name and type matter. But
we accually don't care about the order. Only name and type are allowed
but the order doesn't matter.
2017-09-11 19:56:35 +02:00
Bozhidar Hristov 899b409199 Add tests for phpDocumentor\Reflection\DocBlock::getTags 2017-09-11 19:53:47 +02:00
Bozhidar Hristov b2f473ed77 Update Description.php
Getter for `tags`.
2017-09-11 19:53:47 +02:00
Jaapio 2d3d238c43 Adds name to example tag 2017-08-30 20:51:59 +02:00
Jaapio 1d3a5e8585 Fixes namespace error in ExampleFinder 2017-08-30 20:51:28 +02:00
Jaapio 86e24012a3 Merge remote-tracking branch 'warxcell/empty_var_name' 2017-08-29 21:37:41 +02:00
Bozhidar Hristov b11ada456f Fixes https://github.com/phpDocumentor/ReflectionDocBlock/issues/117 2017-08-28 09:51:41 +03:00
Jaapio 125c8b15c8 Fixes risky tests 2017-08-18 23:01:43 +02:00
Jaapio ac75d9af0a Adds codecoverage reporting 2017-08-18 23:00:55 +02:00
Jaapio c054cfdfe1 Fixes implementation of Example tag 2017-08-18 23:00:12 +02:00
Roberto Espinoza a8d791f8c9 Check tag body has a value before trying to access it as an string array 2017-08-08 08:43:50 +02:00
Roberto Espinoza 4aada1f93c Check tag body has a value before trying to access it as an string array 2017-08-08 08:39:58 +02:00
Jaapio 3c8d2425b5 Drop hhvm support 2017-08-04 23:25:06 +02:00
Jaapio 2b49b7962a Allow see tag to url
The see tag allows Fqsen and uri's. But in the current implementation
only Fqsen where allowed. This wrapps the uri and Fqsen in an uniform class
to be able address them in the same way.

Fixes #78
2017-08-04 23:11:57 +02:00
Jaapio 51911abd63 Stop building for php 5 2017-08-04 23:11:13 +02:00
Jaapio 007a536bc5 Upgrades type-resolver to 0.4.0
Type resolver has renamed some classes.
Dropping php 5.5 support
2017-08-04 23:11:13 +02:00
Jaapio 183824db76 Restores future support for annotations
In #89 the regex to parse tags was to strict. The first character after a tag
had to be a single string. Annotations typically start with a parentheses. Only character not
allowed after a tag is a [.
2017-08-04 22:55:59 +02:00
Jaapio 48d3720bf4 Downgrade phpdocumentor/type-resolver to 0.3
In order to restore a bc break made in 3.2.0 I downgraded the
type-resolver. This makes the version less compatible with php 7.1
But will help our users to upgrade.
2017-08-04 22:52:58 +02:00
Jaapio 46f7e8bb07 Allows usage of compound array types
fixes #50
2017-07-15 13:38:20 +02:00
Jaapio b453d2c304 Allow omitting method return type
Support for `@method myMethod()` was missing but according to the
docs of phpdocumentor this is possible.
2017-07-15 13:38:20 +02:00
Jaapio 8ba1708217 Updates phpunit dependencies 2017-07-15 13:30:40 +02:00
Jaapio 382d7cd6f3 Removes space after tag without description
fixes #86
2017-07-14 18:33:36 +02:00
Jaapio 7c33776cd8 Upgrade typeresolver to 0.4 2017-07-14 16:40:01 +02:00
Aleksei Akireikin 3048f961a3 Unit tests fixed 2017-07-14 16:20:14 +02:00
Jan Schneider 2318e5eb97 Add unit test. 2017-06-04 21:54:23 +02:00
Jan Schneider 47ace60533 Add a tag formatter that aligns all tag values. 2017-06-04 21:54:23 +02:00
Jan Schneider d52fdc6640 Allow to specify a custom tag formatter. 2017-06-04 21:54:23 +02:00
Tomáš Votruba d455663710 travis: add PHP 7.1 2017-06-04 21:52:39 +02:00
Jon Dufresne 7c73155197 Add gitattributes file
Used to allow composer to ignore tests and other development files in
distribution of releases.
2017-05-29 14:23:54 +02:00
Christoph Harms-Ensink a41a31f8c8 UPDATE Method.php, MethodTest.php
- try to make the if-condition php 7.2.0-compatible
- correct docBlock for the test method
2017-05-29 14:21:25 +02:00
Christoph Harms-Ensink e9454d844d UPDATE Method.php, MethodTest.php
- Modify the RegEx, so that an annotation like `@method static $this myMethod()` is parsed correctly
- Write a Unittest for that usecase
2017-05-29 14:21:25 +02:00
Jan Schneider c14a4abfd7 Add test for empty email address. 2017-05-29 14:16:37 +02:00
Jan Schneider f0821ad88f Missed this test. 2017-05-29 14:16:37 +02:00
Jan Schneider a5fb25393a Update tests. 2017-05-29 14:16:37 +02:00
Jan Schneider 8ba65bc4f0 Don't output author email, if it doesn't exist, and add missing space. 2017-05-29 14:16:37 +02:00
Jaap van Otterdijk 1d3dd12a7f Merge pull request #89 from Seldaek/fix_regex
Fix regex for tag name extraction and restore disabled test
2017-04-24 22:45:54 +02:00
Jordi Boggiano 248e5f69dc Fix regex for tag name extraction and restore disabled test 2016-11-14 19:33:41 +01:00
Mike van Riel 8331b5efe8 Merge pull request #79 from Ener-Getick/patch-1
Fix an unexpected behaviour with @deprecated tags
2016-09-30 09:12:33 +02:00
Mike van Riel f574de9fcf Merge pull request #82 from kelunik/issue-81
Escape literal "%" because of vsprintf
2016-09-30 09:11:50 +02:00
Mike van Riel e4a6e492f3 Merge pull request #84 from Seldaek/support_rest_arg
Add support for rest argument notation
2016-09-30 09:11:17 +02:00
Jordi Boggiano 019848728e Add support for rest argument notation 2016-09-28 18:42:19 +02:00
Niklas Keller 4e19318f81 Escape literal "%" because of vsprintf
Fixes #81.
2016-08-23 08:13:57 +02:00
Guilhem N 1be8bc1738 Fix an unexpected behaviour with @deprecated tags 2016-07-18 15:04:51 +02:00
Mike van Riel 9270140b94 Merge pull request #75 from hboomsma/feature/php71_compat
Feature/php71 compat
2016-06-10 11:48:41 +02:00
Hidde Boomsma 02fa9f585e Void is a reserved keyword in PHP7.1.
Running the unit tests with php nightly exposed the bug:

Fatal error: Cannot use phpDocumentor\Reflection\Types\Void as Void
because 'Void' is a special class name in
/home/travis/build/hboomsma/ReflectionDocBlock/tests/unit/DocBlock/Tags/MethodTest.php
on line 25
2016-06-10 11:10:02 +02:00
Mike van Riel ea48fd2c79 Merge pull request #77 from Soullivaneuh/example-to-string
Fix missing Example::__toString method
2016-06-10 09:04:47 +02:00
Sullivan SENECHAL c8bfd60f52 Fix missing Example::__toString method
This method is required by the Tag interface.
2016-06-09 10:39:27 +02:00
Hidde Boomsma 018dc90abb build php nightly 2016-06-08 09:33:05 +02:00
Mike van Riel 45ada3e3fd Merge pull request #73 from hboomsma/feature/typed-array
Allow typed arrays in @method annotation.
2016-06-06 08:44:13 +02:00
Mike van Riel 9a0bd76f6f Merge pull request #72 from fabiang/fix-missing-parenthesis
Fix method name is empty when parenthesis is missing in @method
2016-06-06 08:41:09 +02:00
Hidde Boomsma 10c99960dc Allow typed arrays in @method annotation.
Since the type resolver has support for typed arrays,
I allowed the syntax for the @method annotation.

In effect you can now annotate magic methods like:
    @method Object[] myMethod($arg1, $arg2)
    @method int[] myOtherMethod()
2016-04-07 15:42:51 +02:00
Mike van Riel 52723f0fb8 Add aliases for Context class because newer phpunit versions have a global Context class 2016-02-26 21:44:16 +01:00
Fabian Grutschus 678cf682bf Fix method name is empty when parenthesis is missing in @method 2016-02-26 17:10:44 +01:00
Mike van Riel 332c96dab8 Remove 3.0.x alias from composer.json before tagging 3.0.0 2016-01-28 13:45:51 +01:00
Mike van Riel fc4fe7a67b Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock 2016-01-28 13:29:54 +01:00
Mike van Riel 1900685cf9 Update README for v3 release 2016-01-28 13:29:32 +01:00
Mike van Riel ba00c4ba78 Merge pull request #68 from willemstuursma/patch-1
Add mandatory description element to composer.json
2015-12-24 07:44:45 +01:00
Willem Stuursma 607a0d60d9 Add mandatory description element to composer.json
composer validate gives the following warning: 

````
phpdocumentor/reflection-docblock is valid for simple usage with composer but has
strict errors that make it unable to be published as a package:
description : The property description is required
````
2015-12-22 13:52:16 +01:00
Mike van Riel 82f9aba5a5 Merge pull request #66 from jaapio/feature/filterNullTags
Allow only tags in Docblock argument
2015-10-26 15:52:52 +01:00
Mike van Riel 28632e065c Merge pull request #65 from jaapio/feature/versionBumpTypeResolver
Version bump phpdocumentor/type-resolver
2015-10-26 15:52:38 +01:00
Jaapio e516af3a1b Allow only tags in Docblock argument
The array of tags in the docblock constructor should only contain tags.
Some of the factory methods of the tags are returning a null when the tag could not be created.
This causes issues during parsing. By filtering these null values in the factory this use is resolved.
2015-10-26 15:45:03 +01:00
Jaapio ab334170b7 Version bump phpdocumentor/type-resolver
Due a hotfix done in the the type resolver library version 0.1.5 is the new minimal version of type-resolver.
Without this fix an infinitive loop is created when the use keyword is used in a class.
2015-10-26 15:19:12 +01:00
Mike van Riel 1f637ffba2 Merge pull request #61 from jaapio/hotfix/PassContextToFactory
pass context to tag factory for correct type resolving
2015-08-02 17:12:31 +02:00
Jaapio ff18c828dc pass context to tag factory for correct type resolving 2015-08-02 14:20:58 +02:00
Mike van Riel 0cc2b073b4 Merge pull request #60 from jaapio/fix/returntag
fix type mapping for return tag
2015-07-05 11:46:50 +02:00
Jaapio 6a6a4ca739 add missing @uses 2015-07-05 11:37:49 +02:00
Jaapio 8d24ce351f fix type mapping for return tag 2015-07-05 11:30:12 +02:00
Mike van Riel ed4c6b77ab Write example on escaping values in a DocBlock 2015-06-28 19:49:32 +02:00
Mike van Riel 216cf0025f Add example on writing your own Tag and prepare for TagFactory objects 2015-06-28 11:56:16 +02:00
Mike van Riel a6ffa93e28 Add example and functional test for reconstituting a DocBlock 2015-06-27 16:47:47 +02:00
Mike van Riel 1b5279c777 Add tests for StandardTagFactory and adjust for found bugs 2015-06-27 15:53:47 +02:00
Mike van Riel bcfc8360c1 Fixed indentation error in the travis yml 2015-06-26 13:29:29 +02:00
Mike van Riel 033701111e Ensure that we also test the code after a composer update 2015-06-26 13:25:43 +02:00
Mike van Riel 19c75b3950 Write tests for DescriptionFactory and adjust components for minor bugs that were found 2015-06-26 12:16:45 +02:00
Mike van Riel 09230bda94 Updated dependencies to match other packages 2015-06-26 12:10:13 +02:00
Mike van Riel 50b104f2c0 Add tests for DocBlockFactory and extract interface 2015-06-26 08:59:00 +02:00
Mike van Riel cff8a80680 Add integration test and example on how to read tags 2015-06-24 22:50:12 +02:00
Mike van Riel 97c3735b32 Add first integration test 2015-06-24 08:42:24 +02:00
Mike van Riel de7bc574ea Refactored method tag and added test 2015-06-23 08:28:00 +02:00
Mike van Riel 3b060b555e Refactored the source tag and written test 2015-06-22 08:12:13 +02:00
Mike van Riel d29061ea4d Rewritten Since tag and added test 2015-06-22 07:03:18 +02:00
Mike van Riel 01ddd0ae64 Rewritten Version tag and added test 2015-06-22 07:00:31 +02:00
Mike van Riel c27aeede5d Rewritten Var tag and added test 2015-06-22 06:57:24 +02:00
Mike van Riel 2bab7d9c1f Refactored Uses tag and written test 2015-06-22 06:52:05 +02:00
Mike van Riel 6b92695a71 Refactored throws tag 2015-06-22 06:49:41 +02:00
Mike van Riel 447acda736 Written unit tests for See tag and made it more solid 2015-06-22 06:42:11 +02:00
Mike van Riel 255bc6ffda Written unit tests for return tag 2015-06-22 06:09:54 +02:00
Mike van Riel 75bb275a99 Fixed build fail due to replaced class name 2015-06-21 08:56:53 +02:00
Mike van Riel db3f56cfff Refactored PropertyRead and PropertyWrite tags and added tests 2015-06-21 08:53:18 +02:00
Mike van Riel a7a4d3ff69 Rewritten Property tag and added test 2015-06-21 08:47:34 +02:00
Mike van Riel d1f4ee3c03 Written test for Param tag 2015-06-21 08:38:48 +02:00
Mike van Riel 0c63d0ae5b Rename Other tag class to Generic and write test 2015-06-15 07:04:42 +02:00
Mike van Riel 4b4fc8fdf6 Write test for Link tag 2015-06-15 06:47:27 +02:00
Mike van Riel 7ade5b89fc Write tests for Deprecated tag 2015-06-14 09:11:50 +02:00
Mike van Riel 70eadb02df Add tests for covers tag 2015-06-14 08:50:52 +02:00
Mike van Riel 260a74a77b Expand tests of Author tag with BaseTag covered functionality 2015-06-14 08:18:12 +02:00
Mike van Riel 0d29e96332 Add test for Author Tag 2015-06-14 00:33:59 +02:00
Mike van Riel 8798633221 Add test for passthroughformatter 2015-06-14 00:10:36 +02:00
Mike van Riel 73185b45fd Moved formatters from Description to tags namespace because they only format a Tag now 2015-06-14 00:02:36 +02:00
Mike van Riel 66c45cf480 Update Serializer to match new architecture and add test for it 2015-06-13 23:41:44 +02:00
Mike van Riel e1e2b5cd98 Tweak phpunit configuration and fix mocking errors 2015-06-13 21:46:07 +02:00
Mike van Riel 056607296e Update travis and scrutinizer config 2015-06-13 21:29:32 +02:00
Mike van Riel c24f8ead92 Write test for the Description object and stabilize the API 2015-06-13 21:25:21 +02:00
Mike van Riel 53d5adb324 Descriptions were not separated into tags 2015-06-13 20:27:27 +02:00
Mike van Riel ab3ebf467c Add assertions to DocBlock 2015-06-13 18:41:45 +02:00
Mike van Riel 57c78b2c8b Merge pull request #59 from mvriel/feature/refactor-to-v2
Feature/refactor to v2
2015-06-13 18:31:39 +02:00
Mike van Riel 090cf6b3ad Added assertion library and downgraded phpunit
PHPUnit 4.4 was the last version without phpspec. phpspec conflicts
with this package because it requires v2 of this component and
this causes a cyclic issue with composer
2015-06-13 18:30:22 +02:00
Mike van Riel c150553124 Add getName() method to tag interface 2015-06-13 18:02:21 +02:00
Mike van Riel e586a50170 Remove final from DescriptionFactory; making an interface is overkill 2015-06-13 18:02:05 +02:00
Mike van Riel 21e6a9679a Re-make Link tag in new image 2015-06-13 18:01:26 +02:00
Mike van Riel 5749b814fb Add test for DocBlock class 2015-06-13 18:01:00 +02:00
Mike van Riel b87a111eb2 Remove tests that fail and should be re-made 2015-06-13 18:00:29 +02:00
Mike van Riel 33ab09f4f5 Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock into feature/refactor-to-v2
Conflicts:
	composer.json
2015-06-13 14:32:12 +02:00
Mike van Riel 2c18f0e883 Work towards stabilizing the API.
- Changed Tag to an interface and flattened hierarchy
- Changed Description to accept a list of tags and a template
- Allow auto-wiring when constructing tags
2015-06-13 14:30:43 +02:00
Mike van Riel 2054338d51 Remove old tag tests because they need to be rewritten from scratch 2015-06-13 14:28:28 +02:00
Mike van Riel c80c4b84ee Merge pull request #57 from GrahamCampbell/patch-1
dev-master should always be avoided
2015-06-13 00:18:32 +02:00
Graham Campbell 9440ae1b6b dev-master should always be avoided 2015-06-12 23:17:06 +01:00
Mike van Riel 0574a870e4 Merge pull request #56 from mvriel/feature/refactor-to-v2
Refactored 90% of the library
2015-06-13 00:14:52 +02:00
Mike van Riel 18ef0a8055 Refactored 90% of the library 2015-06-12 20:58:56 +02:00
Mike van Riel b640140928 Merge pull request #54 from mvriel/feature/refactor-to-v2
Add support for types and improve resolution
2015-06-10 14:55:27 +02:00
Mike van Riel 58d09836c1 Add interface for the DocBlockFactory 2015-06-10 14:53:41 +02:00
Mike van Riel 53a142d672 Make resolver final 2015-06-08 08:02:07 +02:00
Mike van Riel b54671f51f Introduce Types
phpDocumentor is capable of representing a whole series of types, more
than PHP supports in fact, and this commit represents those types and a
Resolver that is capable of taking a type Expression and resolving that
to a series of Value Objects representing those types.
2015-06-08 07:05:32 +02:00
Mike van Riel 6e3bf405b3 Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock 2015-06-07 15:07:55 +02:00
Mike van Riel 2e3172c173 Upped master dev version to 3.0 2015-06-07 15:07:32 +02:00
Mike van Riel fab7169255 Add support for types and improve resolution
As part of the re-architecting of phpDocumentor and its Reflection component
we needed to move the type classes from the \phpDocumentor\Descriptor
namespace to \phpDocumentor\Reflection\Types.

In addition to this I have removed the resolution / type creation from the
Collection class into a new Resolver class that is capable of resolving any
type into a Type or Fqsen object.

This is the first commit with the base classes and a test for the Resolver
functionality in subsequent commits we need to add tests for the other
classes and to refactor the collection object.
2015-06-07 11:03:28 +02:00
Mike van Riel bd622adfac Merge pull request #53 from mvriel/feature/refactor-to-v2
Make Context leaner and enable third parties to create them
2015-06-06 21:40:28 +02:00
Mike van Riel f3f4d07808 Make Context leaner and enable third parties to create them
Contexts are necessary for factories to resolve QSEN into FQSENs based
on partial namespaces and namespace aliases. These provide DocBlocks
with the namespace name and namespace aliases.

The new ContextFactory will enable third parties who don't use
phpDocumentor's Reflection component to construct a Context based on
a class reflector or namespace name (and file contents).
2015-06-06 20:03:59 +02:00
Mike van Riel f5e35e0629 [#52] Removed dflydev/markdown from suggested list
The markdown package by DFlyDev is deprecated and is not recommended
anymore due to the provided alternatives (parsedown or commonmark).
2015-05-12 09:21:12 +02:00
Mike van Riel 0862bda1a7 Merge pull request #47 from TomasVotruba/patch-1
travis: PHP 7.0 nightly added
2015-02-27 10:28:18 +01:00
Tomáš Votruba 27a4749a50 travis: PHP 7.0 nightly added
See http://docs.travis-ci.com/user/languages/php/#PHP-7
2015-02-27 10:18:02 +01:00
Mike van Riel 139de61110 Merge pull request #46 from colinodell/remove-composer-lock
Remove composer.lock
2015-02-25 18:26:05 +01:00
Mike van Riel 6af9d09011 Merge pull request #45 from colinodell/commonmark-support
Add support for the league/commonmark Markdown parser
2015-02-25 18:24:05 +01:00
Colin O'Dell 3b76919329 Remove composer.lock
Per the Composer documentation:

> Note: For libraries it is not necessarily recommended to commit the lock file (...)

https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file
2015-02-23 15:03:39 -05:00
Colin O'Dell b268342bf1 Add support for the league/commonmark Markdown parser 2015-02-23 14:50:38 -05:00
Mike van Riel 27848b2a25 Merge pull request #44 from dunglas/patch-1
minor: typo fix in PHPDoc
2015-02-12 13:17:11 +01:00
Kévin Dunglas b735f12f62 minor: typo fix in PHPDoc 2015-02-12 13:08:38 +01:00
Mike van Riel 1d43dcf418 Remove external code coverage 2015-02-03 21:57:02 +01:00
Mike van Riel fa01efa273 Remove external code coverage and fix scrutinizer issues 2015-02-03 21:43:12 +01:00
Mike van Riel 6bddbfdd2b Add scrutinizer config 2015-02-03 13:17:25 +01:00
Mike van Riel 9f929a987a Disable failing test before tagging 2015-02-03 13:10:50 +01:00
Mike van Riel e2d20cf798 Merge pull request #41 from cebe/patch-1
Create LICENSE
2015-02-03 07:38:02 +01:00
Carsten Brandt 92cfb9c8b0 Create LICENSE
According to [composer.json](https://github.com/phpDocumentor/ReflectionDocBlock/blob/master/composer.json#L4) it should be MIT.

fixes #40
2014-12-19 23:13:47 +01:00
Chuck Burgess 783f450ee6 Merge pull request #39 from mvriel/feature/phpDocumentor2/42
Add support for DocBlock template markers
2014-09-02 09:26:20 -05:00
Mike van Riel 6142bbbbbf Add missing DocBlock (info). 2014-08-30 11:16:26 +02:00
Mike van Riel fe8652b292 Add support for DocBlock template markers
DocBlocks may start with #@+ and #@- to indicate that they are (the start) of a DocBlock
template or the end of a template.

In this commit I have changed the way a DocBlock is parsed to interpret this information
and added tests to show for it. In addition I have added more comments to the Regular
Expression responsible for splitting a DocBlock to show the business rules more clearly.

This is the first step in implementing https://github.com/phpDocumentor/phpDocumentor2/issues/42.
2014-08-30 11:08:15 +02:00
Mike van Riel 70bca88316 Merge pull request #38 from GrahamCampbell/stuff
Composer And Travis Updates
2014-08-21 23:05:07 +02:00
Graham Campbell cb7c16fb61 Travis improvements 2014-08-21 13:02:49 +01:00
Graham Campbell 0233433e59 Composer updates 2014-08-21 13:02:41 +01:00
Mike van Riel c830f38cf3 Merge pull request #37 from alexkn/fix-error-display
Remove Error display at MethodTag
2014-08-09 12:27:07 +02:00
Alexander Knöbel 236c7c7961 Remove Error display at MethodTag 2014-08-09 12:09:15 +02:00
Mike van Riel 0d8a07252b Merge pull request #33 from Nyholm/patch-1
Added PHP 5.6 and HHVM to travis.yml
2014-07-19 08:49:33 +02:00
Tobias Nyholm b4cd037a02 Added hhvm-nightly 2014-07-09 14:15:10 +02:00
Tobias Nyholm 37bb216b95 Added PHP 5.6 and HHVM to travis.yml 2014-07-09 12:05:21 +02:00
Mike van Riel 5f8ee928b6 Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock 2014-04-26 12:10:44 +02:00
Mike van Riel d798405fae Implement support for Variadic arguments
Fixes https://github.com/phpDocumentor/phpDocumentor2/issues/629, in
this commit we add support for recognizing and displaying variadic
arguments as described in the Variadics RFC on Internals
(https://wiki.php.net/rfc/variadics).

This adds support for describing Variadics even before PHP 5.6, where
this feature is planned.
2014-03-28 10:21:30 +01:00
Mike van Riel aee778bec6 Merge pull request #31 from siad007/patch-1
Fixed method call.
2014-03-16 13:31:01 +01:00
Siad Ardroumli 832559be31 Fixed method call.
Related to https://github.com/phpDocumentor/phpDocumentor2/pull/1145
2014-03-16 13:23:37 +01:00
Mike van Riel 54c707b480 Merge pull request #30 from cebe/preserve-newlines
Preserve newlines in docblock tags
2014-03-01 11:01:55 +01:00
Carsten Brandt 4922a4a286 Preserve newlines in docblock tags
This is especially important when using markdown.
Adding a blank line between text introduces a new paragraph.
Current implementation will result in all text staying in one paragraph
and also other elements like lists and code do not get recognized in
most cases.
2014-02-28 17:17:48 +01:00
Mike van Riel 506de88c26 Add support for Parsedown as a markdown parser 2013-12-05 09:16:55 +01:00
Vasil Rangelov d67d5f41ee Merge pull request #25 from barryvdh/patch-1
Markdown is not required, so move to suggest
2013-08-08 09:31:39 -07:00
Barry vd. Heuvel 7a5d99cd4f Markdown is not required, so move to suggest
Markdown is only used once and a check is in place to see if the markdown classes exists. So perhaps it is better to move this to suggest instead of require, so the people who don't need it, don't have to download it.
2013-08-08 18:25:04 +02:00
Vasil Rangelov 57eadf5708 Merge pull request #24 from tommygnr/travis-5.5
Enable travis builds on php5.5
2013-08-07 04:04:22 -07:00
Tom Corrigan fbecde4331 Enable travis builds on php5.5 2013-08-07 13:08:11 +10:00
Mike van Riel ec3d9f5c39 Merge pull request #23 from tommygnr/patch-1
Add a branch alias
2013-08-01 12:16:50 -07:00
Tom Corrigan 0814579afd Add a branch alias
This will enable improved version constraints in phpdocumentor/reflection
2013-08-02 02:40:14 +10:00
Vasil Rangelov 49c718367a Merge pull request #22 from barryvdh/tostring
Add __toString() methods for Description and Tag
2013-05-27 10:54:22 -07:00
Barry vd. Heuvel 21148759ac Add __toString() methods for Description and Tag
And let the Serializer make use of the (string) $tag
2013-05-27 18:16:15 +02:00
Vasil Rangelov 5000a2878d Added "{}" around all double quoted variables, for readability's sake;
Performance improvement in Serializer - wrap length is calculated once during the text portion only. Tags reuse the result. Also no "prefix" adding in tags - the name is simply added before wrapping.
2013-05-27 02:04:23 +03:00
Vasil Rangelov a2aae72328 Minor doc fix at Serializer.php. 2013-05-27 01:31:58 +03:00
Vasil Rangelov 5b2b43e2a9 Added getters for Serializer options;
Swapped the indent and indent string options at Serializer's constructor;
Renamed Serializer::setIndentFirstLine() to setIsFirstLineIndented() in accordance with the getter (PHPMD fix);
Line length is now ACTUALLY line length, i.e. it takes the indentation into account, and is applied to tags as well;
Fixed ReturnTag::setContent() to set "types" to NULL;
A lot of doc and CS fixes at Serializer.php.
2013-05-27 01:27:07 +03:00
Vasil Rangelov f910025d29 Merge pull request #20 from barryvdh/master
Export docblock comment
2013-05-26 13:55:34 -07:00
Barry vd. Heuvel 6ac49cd709 Revert setType
Doesn't really belong to this PR
2013-05-26 22:36:53 +02:00
Barry vd. Heuvel eb4ab2c720 Move serializer to seperate class 2013-05-26 22:36:31 +02:00
Barry vd. Heuvel f331d328a4 Export DocBlock & full description
Add get/set for entire description, and create a docblock comment, based
on the description/tags
2013-05-26 21:17:09 +02:00
Barry vd. Heuvel 3760d10ace Set return type 2013-05-26 21:16:30 +02:00
Vasil Rangelov d99732612a Added support for static method declarations at MethodTag and according unit tests.
Fixed MethodTag::getContent() to actually return the content as opposed to $this;
2013-05-16 22:17:15 +03:00
Vasil Rangelov 7f55602948 Adjusted Unit tests and docs to match the latest dot separation. 2013-04-16 19:25:40 +03:00
Vasil Rangelov 510159bace Fixed the dot separation to match the latest PSR
(see phpDocumentor/phpDocumentor2#797)
2013-04-16 17:22:15 +03:00
Mike van Riel e06ea450a4 Merge pull request #17 from joncave/cotnent-typo
Fix typo in "cotnent"
2013-02-01 10:47:35 -08:00
Jon Cave 8f7ec6bd4a Fix typo in "cotnent" 2013-02-01 18:08:30 +00:00
Vasil Rangelov 13466286b0 Added "scalar" as a recognized keyword (phpDocumentor/phpDocumentor2#694);
Changed the list of keywords to be static (for the purpose of reducing memory consumption);
Updated composer.lock with the latest dependencies (PHPUnit in particular).
2012-12-02 22:26:45 +02:00
Vasil Rangelov e2528539ac Added a Travis status image to README.md;
Also, fixed a typo.
2012-11-30 22:43:34 +02:00
Vasil Rangelov ff09e61782 Added setters at Location and Description;
Added DocBlock::appendTag();
Minor reorganization at the tag setters;
2012-11-30 22:37:41 +02:00
Vasil Rangelov 8223e475fa Refactored all tags to have setters for all of their components;
Removed the special handling for VarTag (it's now equivalent to ParamTag);
Minor doc, CS and coverage fixes.
2012-11-30 19:26:19 +02:00
Vasil Rangelov bad318bc39 Adjusted composer files for consistency with PhpDocumentor. 2012-11-29 20:12:53 +02:00
Vasil Rangelov 23dedb3e10 CS fixes. 2012-11-27 19:52:28 +02:00
Vasil Rangelov 5712aa6efd Added @boenrobot to Travis' email notifications;
Some CS fixes at TagTest.php.
2012-11-22 13:22:00 +02:00
Vasil Rangelov afd4645858 Merge pull request #15 from ashnazg/make-build
Make travis build
2012-11-22 03:03:34 -08:00
Chuck Burgess a7e0e19229 restore original 2012-11-21 19:16:31 -06:00
Chuck Burgess b102a8d9c5 graphviz isn't necessary 2012-11-21 19:15:29 -06:00
Chuck Burgess 8e0a07cbd8 use phpunit in vendor 2012-11-21 19:08:28 -06:00
Chuck Burgess 62f64a3423 restore color=true 2012-11-21 19:05:59 -06:00
Vasil Rangelov bf3e86788d Added tests related to the namespaced tag support;
Restored ReturnTag::getTypesCollection() to "protected", to avoid potential BC breaks later.
2012-11-22 01:23:31 +02:00
Vasil Rangelov 2dbc608a51 Added support for namespaced tags;
Simplified @see and @link parsing;
Added comments to the regexes of @method, @example and @source;
Added a test case for what 2812eac046 intended to fix.
2012-11-22 00:37:22 +02:00
Chuck Burgess 6804adcc87 initial travis build 2012-11-21 15:09:44 -06:00
Chuck Burgess 658d11b7b5 add --dev deps 2012-11-21 15:09:22 -06:00
Chuck Burgess a4d8641dea tighten up dist file 2012-11-21 15:08:31 -06:00
Vasil Rangelov 3e91fb4071 Merge pull request #13 from boenrobot/location
Abstracting away namespace (and other context dependent) information into a new object
2012-11-21 12:36:31 -08:00
Vasil Rangelov 8bb304309c Introduced Context and Location, and adapted Collection and ReturnTag accordingly. 2012-11-21 15:55:10 +02:00
Vasil Rangelov a4b899e96c Reverted the move of explode() into Return, and moved the implode() into Collection's new __toString() method instead;
Also had to made type resolution lazy, as a pleasant side effect.

This reverts commit db20ae39fb.
2012-11-18 18:50:45 +02:00
Vasil Rangelov cee63f991d Revert "Merge pull request #10 from boenrobot/author"
This reverts commit 21c36677ab, reversing
changes made to ffcaa03337.
2012-11-18 17:15:48 +02:00
Vasil Rangelov 8df7e5fb6b Removed redundant preg_split from SourceTag (mistakenly pasted from ReturnTag). 2012-11-17 17:32:48 +02:00
Vasil Rangelov c33dc9e7d7 Merge pull request #10 from boenrobot/author
Introduced role, description and space separated URIs to the author tag.
2012-11-17 06:33:38 -08:00
Vasil Rangelov 77d0359016 Merge pull request #12 from boenrobot/source-and-example
Reflections for @source and @example
2012-11-17 05:23:56 -08:00
Vasil Rangelov 86c72b291a Added @example tag handler, and registered it and @source at Tag. 2012-11-17 15:23:16 +02:00
Vasil Rangelov c70be2a745 Added reflection for @source tag. 2012-11-17 15:16:56 +02:00
Vasil Rangelov 29dcb18b95 Merge pull request #11 from boenrobot/version-and-derivatives
Reflections for @version, @since and @deprecated
2012-11-17 05:13:04 -08:00
Vasil Rangelov 44cf524dcf Simplified ReturnTag parsing. 2012-11-16 21:53:17 +02:00
Vasil Rangelov a4855850d3 Moved the type separation into ReturnTag, for consistency with the type merging that is currently there. 2012-11-16 21:43:25 +02:00
Vasil Rangelov 63a8fb34d4 Added a limit on Collection's explode(), thus (insignificantly, but still) improving performance. 2012-11-14 22:42:56 +02:00
Vasil Rangelov 09b2cb083d Fixed DocBlock giving and reception for long descriptions. 2012-11-14 18:05:03 +02:00
Vasil Rangelov 3bfb48da76 Doc updates and fixes. 2012-11-13 21:50:56 +02:00
Vasil Rangelov 92572a9982 Updated @author in accordance with the latest changes. 2012-11-13 19:23:42 +02:00
Vasil Rangelov 532fb040ab Merge branch 'master' of github.com:boenrobot/ReflectionDocBlock into author
Conflicts:
	src/phpDocumentor/Reflection/DocBlock/Tag/AuthorTag.php
2012-11-13 19:13:34 +02:00
Vasil Rangelov fc53ad4139 Updated @version in accordance with the latest changes in Tag. 2012-11-13 19:10:13 +02:00
Vasil Rangelov 3d8bcdbe5b Merge branch 'master' of github.com:boenrobot/ReflectionDocBlock into version-and-derivatives 2012-11-13 19:05:14 +02:00
Vasil Rangelov 878e24d40d Made all tag handlers call Tag::__construct() rather than "manually" duplicating it;
Tag::__construct() trims the description (as is common for most tag handlers), while the original contents is still in the $content property;
Added the DocBlock argument to all tag handlers.
2012-11-13 19:00:49 +02:00
Vasil Rangelov 903722e389 Renamed LongDescription to Description, to better serve its new dual role as "holder for a place where inline tags can occur";
Removed Tag::setDocblock() in favor of an additional constructor argument that defaults to NULL;
Tag::createInstance() and Description's constructor now have a second argument, allowing the specification of an owning DocBlock;
Description::getParsedContents() assigns the Description's owning DocBlock object when creating tags.
2012-11-13 17:16:30 +02:00
Vasil Rangelov ea62320415 Tweaked the "testInvalidTagBlock" test to appease PHPCS (though strictly speaking, this is a bug with PHPCS "NEWDOC" handling). 2012-11-13 16:43:36 +02:00
Vasil Rangelov 8107678560 Added reflections for @version, @since and @deprecated, which separate the version vector (if one is provided) from the description. 2012-11-13 15:28:17 +02:00
Vasil Rangelov 6602ce0375 @return now trims the content before splitting it;
Removed ThrowTag.php (unnecessary, given the map, which aliases "throw" to ThrowsTag.php);
Added tests for ThrowsTag, along with a few other minor test additions and fixes;
2012-11-11 19:51:04 +02:00
Vasil Rangelov 2348c16485 Applied multi line fixes to @param, analogous to those in @return. 2012-11-11 17:45:16 +02:00
Vasil Rangelov b802727676 Minor syntax and doc fixes at Tag::registerTagHandler();
Split the "testTagHandlerRegistration" test into several new ones, with appropriate @covers annotations added;
Although not required for single liners, class names at the built in tag handlers map are indented on a separate line for readability.
2012-11-11 15:20:59 +02:00
Vasil Rangelov 08dc71ba37 Refactored Tag::createInstance() to use a simple tag-to-class map, that has the default tag handlers pre-registered. 2012-11-11 00:54:51 +02:00
Vasil Rangelov d73444f859 Minor doc fixes. 2012-11-10 23:45:28 +02:00
Vasil Rangelov f11936eaae Removed DocBlock::expandType() and associated tests, as previously advised by @mvriel;
Added tests for generic Tag objects, and a few others;
Increased total coverage by more appropriate use of @covers annotations.
2012-11-10 23:19:36 +02:00
Vasil Rangelov 6e1bb192b3 Inverted @param and @return hierarchy;
More fixes to tests and code coverage increase.
2012-11-10 20:27:57 +02:00
Vasil Rangelov 038a5f3150 Introduced role, description and space separated URIs to the author tag. 2012-11-10 16:50:39 +02:00
Vasil Rangelov ad32c225c5 Updated tag doc comments. 2012-11-10 14:18:40 +02:00
Vasil Rangelov ca90350e36 Made the Tag::createInstance() create generic tag objects when there are uppercase letters in the tag name
(this fixes phpDocumentor/phpDocumentor2#672).
2012-11-10 14:00:01 +02:00
Vasil Rangelov 19a9124274 Increased unit test coverage of DocBlock;
Moved the tag block checks outside (and prior to) the tag line loop;
Doc and CS fixes.
2012-11-10 13:24:46 +02:00
Vasil Rangelov 1a5e882877 Merge pull request #9 from boenrobot/LongDescription
Nested inline tag parsing
2012-11-10 01:52:46 -08:00
Vasil Rangelov d58be52929 Merge branch 'LongDescription' of github.com:boenrobot/ReflectionDocBlock into LongDescription 2012-11-10 11:51:40 +02:00
Vasil Rangelov 348177c938 Improved performance, thanks to @nikic's new regex. 2012-11-10 11:49:23 +02:00
Vasil Rangelov 66b35473ec Added escape sequences that allow "literal" inline tags in descriptions. 2012-11-10 11:49:23 +02:00
Vasil Rangelov 4bb2c04673 Implemented nested inline tag parsing;
Added unit tests for LongDescription.php;
Added the "src" folder as white listed for code coverage in the PHPUnit configuration;
Fixed the @covers annotation inside the CoversTagTest.php (isn't this ironic?).
2012-11-10 11:49:23 +02:00
Vasil Rangelov 36b46b9769 Merge pull request #8 from boenrobot/CS
Coding standard fixes.
2012-11-10 01:40:09 -08:00
Vasil Rangelov df67eaf0be Restored indentation in multi-line tag descriptions, and applied them where they were previously missing. 2012-11-05 23:14:32 +02:00
Vasil Rangelov 6bc655072f Improved performance, thanks to @nikic's new regex. 2012-11-05 17:50:11 +02:00
Vasil Rangelov f7457e64bf Added escape sequences that allow "literal" inline tags in descriptions. 2012-11-04 23:45:55 +02:00
Vasil Rangelov e04f25a77b Shortened some long variable names in the test suite, as advised by PHPMD's default settings. 2012-11-04 23:34:25 +02:00
Vasil Rangelov d31a33e846 Implemented nested inline tag parsing;
Added unit tests for LongDescription.php;
Added the "src" folder as white listed for code coverage in the PHPUnit configuration;
Fixed the @covers annotation inside the CoversTagTest.php (isn't this ironic?).
2012-11-04 22:29:38 +02:00
Vasil Rangelov 54f30f83b6 Updated comments with the namespaced notation, and added the "Tag" suffix where needed. 2012-11-04 22:19:18 +02:00
Vasil Rangelov bb189b87bd Made PSR2 related fixes that are compatible with the PEAR coding standard. 2012-11-04 16:02:57 +02:00
Vasil Rangelov 9ea3275389 Tons of coding standard fixes. 2012-11-04 15:16:37 +02:00
Mike van Riel 0701e60839 Change behaviour of @param parsing
In issue report phpDocumentor/phpDocumentor2#620 @bobef reported that when he
used just a Type as content of the @param that it would be recognized as
description instead of the Type.

According to the unit tests this is correct behaviour but after reviewing the
pattern of the output his version is more consistent. As such I have altered
the behaviour to act as following:

If only one word is found after an @param (word means white-space bounded
series of characters) then interpret that as the type and not description.

During this item several issues in unit tests were fixed and a new 'Type'
Collection was introduced that is capable of expanding types based on a given
namespace and series of aliases.
This should be re-used in phpDocumentor's Transformer as a duplication exists
there with the expanding of the Types.

Please note: the suggested format by @bobef is not valid according to the
PHPDoc Standard but is provided for convenience.
2012-11-03 22:14:43 +01:00
Mike van Riel b3641c0e69 Merge branch 'patch-2' of https://github.com/boenrobot/ReflectionDocBlock into boenrobot-patch-2
Conflicts:
	src/phpDocumentor/Reflection/DocBlock/LongDescription.php
2012-11-01 18:56:36 +01:00
Vasil Rangelov b028b5eb44 Restored the greedy-ness inversion. 2012-10-31 11:28:53 +02:00
Vasil Rangelov f001c3cd92 Removed LongDescription::getTags() and made parsing to occur only the first time it's requested. 2012-10-17 17:33:52 +03:00
Mike van Riel 9e5e386120 Merge pull request #7 from boenrobot/patch-3
Reflection for the author tag.
2012-10-15 13:01:19 -07:00
Vasil Rangelov 6ff52dfc59 Added doc blocks to the new methods. 2012-10-15 13:17:51 +03:00
Mike van Riel d5dc80a443 Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock 2012-09-30 14:29:16 +02:00
Mike van Riel b5e8c5cb05 Fix @return type/description seperation
Per issue phpDocumentor/phpDocumentor2#623 should a newline directly behind the type
of a multiline @return tag be interpreted correctly. Currently seperation occurs
on the first space or tab but this is not sufficient.
2012-09-30 14:26:28 +02:00
Vasil Rangelov 50e7366bed Added Tag/AuthorTag.php. 2012-09-30 01:47:50 +03:00
Vasil Rangelov a2bf8995dc Added Tag::getParsedDescription();
Minor performance tweak at LongDescription.
2012-09-26 16:27:32 +03:00
Vasil Rangelov ddc3005eea Added doc block to getParsedContents(). 2012-09-22 05:56:37 +03:00
Vasil Rangelov c501553216 Added parsed inline tags. 2012-09-22 05:41:10 +03:00
Mike van Riel feeea6b7c4 Merge pull request #5 from boenrobot/patch-1
Fix for phpDocumentor2#562
2012-09-16 08:15:18 -07:00
Mike van Riel 58aab9c891 Multiline @return statements were stripped from their newlines and indent
@return statements (and effectively others) were stripped from their newlines
and indentation. By tweaking the reflection a bit was this effect countered.
2012-09-10 16:50:44 +02:00
Vasil Rangelov 9e0a3921b3 Ensured key consistency. 2012-08-12 23:53:31 +03:00
Vasil Rangelov e8ccebaf17 Fix for phpDocumentor2#562
Possible fix for phpDocumentor/phpDocumentor2#562.
2012-08-12 20:21:19 +03:00
Mike van Riel cd7233e50a #544: Added self and $this to the exceptions where type expansion is not required 2012-07-27 06:56:37 +02:00
Mike van Riel eb8fb7a7ac Removed the prefixing slash in a class_exists call because the autoloader of Composer
dies on that occasionally.
2012-07-26 17:09:50 +02:00
Mike van Riel 49040c9104 Fixing the other RegExes as well since they were also not using the u modifier 2012-07-13 20:07:51 +02:00
Mike van Riel cfc74b22ae Merge pull request #4 from rvanvelzen/master
Add the u modifier to the regexes used.
2012-07-13 10:28:21 -07:00
Richard van Velzen efd8102f3e Merge branch 'master' of git://github.com/phpDocumentor/ReflectionDocBlock 2012-07-13 13:43:29 +02:00
Richard van Velzen a7b3df8c5b Add the u modifier to the regexes used.
Without the u modifier, PCRE does not recognize Unicode sequences, which breaks certain cases.
2012-07-13 13:42:49 +02:00
Mike van Riel b3d119fd24 Namespace resolution did not work as intended
The algorithm to expand a class name into a FCQN contained seevral errors.
These are now gone and expansion should work as expected
2012-06-30 13:38:18 +02:00
Mike van Riel cb0246462f Added 'global' to the list of special namespace names indicating global space and adding namespace resolution to the param tags 'getType()' method 2012-06-29 23:04:12 +02:00
Mike van Riel 467101e53d Added command to set the DocBlock onto the tags so that type expansion may happen 2012-06-21 23:03:48 +02:00
Mike van Riel 0a90ca3881 Changed return tag to properly support expanding types 2012-06-21 23:00:13 +02:00
Mike van Riel fa9e0b637e Added type expansion for the @param tag 2012-06-21 22:51:29 +02:00
Mike van Riel 34ab54aaca Added support for namespace expansion of a DocBlock and via the DocBlock to its tags 2012-06-21 22:17:30 +02:00
Mike van Riel 11f904aae9 Merge pull request #3 from rvanvelzen/master
Fix phpDocumentor/phpDocumentor2#467
2012-06-04 13:34:54 -07:00
Richard van Velzen e29bba03f6 Fixed the case where the dot does not properly terminate the short description.
The regular expression only took into account newlines, not general whitespace after the dot. Added a test case as well.
2012-06-04 09:27:56 +02:00
Mike van Riel b5b35d2690 Updated README to reflect submission to packagist 2012-06-02 22:07:17 +02:00
Mike van Riel 715d1e0244 Merge pull request #2 from egeniq/master
Small path fix
2012-06-02 13:00:11 -07:00
= 594a569a1a Fix for relative paths 2012-06-02 21:44:44 +02:00
Mike van Riel bf9793aab3 Merge branch 'master' of github.com:phpDocumentor/ReflectionDocBlock 2012-05-26 10:29:51 +02:00
Mike van Riel d6955a0a13 Merge pull request #1 from leofeyer/master
Broken markdown support for long descriptions
2012-05-14 23:26:52 -07:00
Leo Feyer 5aea3269e1 This will bring back the markdown parser to long descriptions 2012-05-14 17:35:02 +02:00
189 changed files with 17452 additions and 1904 deletions
+17
View File
@@ -0,0 +1,17 @@
/.gitattributes export-ignore
/.gitignore export-ignore
/.yamllint.yaml export-ignore
/composer-require-checker.json export-ignore
/composer.lock export-ignore
/phpmd.xml.dist export-ignore
/phpunit.xml.dist export-ignore
/Makefile export-ignore
/phive.xml export-ignore
/phpcs.xml.dist export-ignore
/phpstan.neon export-ignore
/phpstan-baseline.neon export-ignore
/psalm.xml export-ignore
/phpdoc.dist.xml export-ignore
/tests/ export-ignore
/docs/ export-ignore
/.github/ export-ignore
+12
View File
@@ -0,0 +1,12 @@
version: 2
updates:
- package-ecosystem: "composer"
directory: "/"
schedule:
interval: "daily"
open-pull-requests-limit: 10
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
+19
View File
@@ -0,0 +1,19 @@
# https://docs.github.com/en/actions
name: "Documentation"
on: # yamllint disable-line rule:truthy
push:
branches:
- "6.x"
workflow_dispatch: null
jobs:
run:
name: "Documentation"
uses: "phpDocumentor/.github/.github/workflows/documentation.yml@main"
with:
deploy: true
component: "reflection-docblock"
secrets:
token: "${{ secrets.BOT_TOKEN }}"
+58
View File
@@ -0,0 +1,58 @@
# https://docs.github.com/en/actions
name: "Integrate"
on: # yamllint disable-line rule:truthy
push:
branches:
- "6.x"
pull_request: null
# Allow manually triggering the workflow.
workflow_dispatch: null
jobs:
code-coverage:
name: "Code Coverage"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-root-version: "6.x-dev"
coding-standards:
name: "Coding Standards"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-root-version: "6.x-dev"
dependency-analysis:
name: "Dependency analysis"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-root-version: "6.x-dev"
lint-root:
name: "Lint root"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-options: "--no-check-publish --ansi"
static-analysis:
name: "Static analysis"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
php-extensions: "none, ctype, dom, json, mbstring, phar, simplexml, tokenizer, xml, xmlwriter, fileinfo, pcntl, posix"
composer-root-version: "6.x-dev"
unit-tests:
name: "Unit test"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-root-version: "6.x-dev"
upcoming-releases: true
integration-tests:
name: "Integration test"
uses: "phpDocumentor/.github/.github/workflows/[email protected]"
with:
composer-root-version: "6.x-dev"
upcoming-releases: true
test-suite: "integration"
+20 -1
View File
@@ -1 +1,20 @@
.idea
# IDE Shizzle; it is recommended to use a global .gitignore for this but since this is an OSS project we want to make
# it easy to contribute
.idea
/nbproject/private/
.buildpath
.project
.settings
# Build folder and vendor folder are generated code; no need to version this
build/
temp/
tools/
vendor/
*.phar
# By default the phpunit.xml.dist is provided; you can override this using a local config file
phpunit.xml
.phpunit.result.cache
.phpdoc
+65
View File
@@ -0,0 +1,65 @@
extends: "default"
ignore: |
.build/
.notes/
vendor/
rules:
braces:
max-spaces-inside-empty: 0
max-spaces-inside: 1
min-spaces-inside-empty: 0
min-spaces-inside: 1
brackets:
max-spaces-inside-empty: 0
max-spaces-inside: 0
min-spaces-inside-empty: 0
min-spaces-inside: 0
colons:
max-spaces-after: 1
max-spaces-before: 0
commas:
max-spaces-after: 1
max-spaces-before: 0
min-spaces-after: 1
comments:
ignore-shebangs: true
min-spaces-from-content: 1
require-starting-space: true
comments-indentation: "enable"
document-end:
present: false
document-start:
present: false
indentation:
check-multi-line-strings: false
indent-sequences: true
spaces: 2
empty-lines:
max-end: 0
max-start: 0
max: 1
empty-values:
forbid-in-block-mappings: true
forbid-in-flow-mappings: true
hyphens:
max-spaces-after: 2
key-duplicates: "enable"
key-ordering: "disable"
line-length: "disable"
new-line-at-end-of-file: "enable"
new-lines:
type: "unix"
octal-values:
forbid-implicit-octal: true
quoted-strings:
quote-type: "double"
trailing-spaces: "enable"
truthy:
allowed-values:
- "false"
- "true"
yaml-files:
- "*.yaml"
- "*.yml"
+21
View File
@@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2010 Mike van Riel
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
+47
View File
@@ -0,0 +1,47 @@
.PHONY: help
help: ## Displays this list of targets with descriptions
@grep -E '^[a-zA-Z0-9_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[32m%-30s\033[0m %s\n", $$1, $$2}'
.PHONY: code-style
code-style:
docker run -it --rm -v${PWD}:/opt/project -w /opt/project phpdoc/phpcs-ga:latest -d memory_limit=1024M -s
.PHONY: fix-code-style
fix-code-style:
docker run -it --rm -v${PWD}:/opt/project -w /opt/project phpdoc/phpcs-ga:latest phpcbf
.PHONY: static-code-analysis
static-code-analysis: vendor ## Runs a static code analysis with phpstan/phpstan and vimeo/psalm
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 vendor/bin/phpstan --configuration=phpstan.neon --memory-limit=1024M
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 vendor/bin/psalm.phar
.PHONY: test
test: test-unit ## Runs all test suites with phpunit/phpunit
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 vendor/bin/phpunit
.PHONY: test-unit
test-unit: ## Runs unit tests with phpunit/phpunit
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 vendor/bin/phpunit --testsuite=unit
.PHONY: dependency-analysis
dependency-analysis: vendor ## Runs a dependency analysis with maglnet/composer-require-checker
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 .phive/composer-require-checker check --config-file=/opt/project/composer-require-checker.json
vendor: composer.json composer.lock
composer validate --no-check-publish
composer install --no-interaction --no-progress
.PHONY: benchmark
benchmark:
docker run -it --rm -v${CURDIR}:/opt/project -w /opt/project php:7.4-cli tools/phpbench run
.PHONY: rector
rector: ## Refactor code using rector
docker run -it --rm -v${PWD}:/opt/project -w /opt/project php:7.4 vendor/bin/rector process
.PHONY: pre-commit-test
pre-commit-test: fix-code-style test code-style static-code-analysis
.PHONY: docs
docs: ## Generate documentation with phpDocumentor
docker run -it --rm -v${PWD}:/opt/project -w /opt/project phpdoc/phpdoc:3
+50 -33
View File
@@ -1,5 +1,12 @@
The ReflectionDocBlock Component
================================
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
[![Integrate](https://github.com/phpDocumentor/ReflectionDocBlock/actions/workflows/integrate.yaml/badge.svg)](https://github.com/phpDocumentor/ReflectionDocBlock/actions/workflows/integrate.yaml)
[![Scrutinizer Code Coverage](https://img.shields.io/scrutinizer/coverage/g/phpDocumentor/ReflectionDocBlock.svg)](https://scrutinizer-ci.com/g/phpDocumentor/ReflectionDocBlock/?branch=master)
[![Scrutinizer Code Quality](https://img.shields.io/scrutinizer/g/phpDocumentor/ReflectionDocBlock.svg)](https://scrutinizer-ci.com/g/phpDocumentor/ReflectionDocBlock/?branch=master)
[![Stable Version](https://img.shields.io/packagist/v/phpdocumentor/reflection-docblock.svg?label=stable)](https://packagist.org/packages/phpdocumentor/reflection-docblock)
[![Unstable Version](https://img.shields.io/packagist/v/phpdocumentor/reflection-docblock.svg?include_prereleases&label=unstable)](https://packagist.org/packages/phpdocumentor/reflection-docblock)
ReflectionDocBlock
==================
Introduction
------------
@@ -7,51 +14,61 @@ Introduction
The ReflectionDocBlock component of phpDocumentor provides a DocBlock parser
that is 100% compatible with the [PHPDoc standard](http://phpdoc.org/docs/latest).
With this component can a library provide support for annotations via DocBlocks
With this component, a library can provide support for annotations via DocBlocks
or otherwise retrieve information that is embedded in a DocBlock.
> **Note**: *this is a core component of phpDocumentor and is constantly being
> optimized for performance.*
Installation
------------
You can install the component in the following ways:
* Use the official Github repository (https://github.com/phpDocumentor/ReflectionDocBlock)
* Via composer (add the Github Repository as VCS repository in your composer.yml)
```bash
composer require phpdocumentor/reflection-docblock
```
Usage
-----
The ReflectionDocBlock component is designed to work in an identical fashion to
PHP's own Reflection extension (http://php.net/manual/en/book.reflection.php).
In order to parse the DocBlock one needs a DocBlockFactory that can be
instantiated using its `createInstance` factory method like this:
Parsing can be initiated by instantiating the
`\phpDocumentor\Reflection\DocBlock()` class and passing it a string containing
a DocBlock (including asterisks) or by passing an object supporting the
`getDocComment()` method.
```php
$factory = \phpDocumentor\Reflection\DocBlockFactory::createInstance();
```
> *Examples of objects having the `getDocComment()` method are the
> `ReflectionClass` and the `ReflectionMethod` classes of the PHP
> Reflection extension*
Then we can use the `create` method of the factory to interpret the DocBlock.
Please note that it is also possible to provide a class that has the
`getDocComment()` method, such as an object of type `ReflectionClass`, the
create method will read that if it exists.
Example:
```php
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* This is a Description. A Summary and Description are separated by either
* two subsequent newlines (thus a whiteline in between as can be seen in this
* example), or when the Summary ends with a dot (`.`) and some form of
* whitespace.
*/
DOCCOMMENT;
$class = new ReflectionClass('MyClass');
$phpdoc = new \phpDocumentor\Reflection\DocBlock($class);
$docblock = $factory->create($docComment);
```
or
The `create` method will yield an object of type `\phpDocumentor\Reflection\DocBlock`
whose methods can be queried:
$docblock = <<<DOCBLOCK
/**
* This is a short description.
*
* This is a *long* description.
*
* @return void
*/
DOCBLOCK;
```php
// Contains the summary for this DocBlock
$summary = $docblock->getSummary();
$phpdoc = new \phpDocumentor\Reflection\DocBlock($docblock);
// Contains \phpDocumentor\Reflection\DocBlock\Description object
$description = $docblock->getDescription();
// You can either cast it to string
$description = (string) $docblock->getDescription();
// Or use the render method to get a string representation of the Description.
$description = $docblock->getDescription()->render();
```
> For more examples it would be best to review the scripts in the [`/examples` folder](/examples).
+16
View File
@@ -0,0 +1,16 @@
{
"symbol-whitelist" : [
"null", "true", "false",
"static", "self", "parent",
"array", "string", "int", "float", "bool", "iterable", "callable", "void", "object", "XSLTProcessor",
"PHPStan\\PhpDocParser\\ParserConfig"
],
"php-core-extensions" : [
"Core",
"pcre",
"Reflection",
"tokenizer",
"SPL",
"standard"
]
}
+50 -7
View File
@@ -1,15 +1,58 @@
{
"name": "phpdocumentor/reflection-docblock",
"type": "library",
"name": "phpdocumentor/reflection-docblock",
"description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.",
"type": "library",
"license": "MIT",
"authors": [
{"name": "Mike van Riel", "email": "[email protected]"}
{
"name": "Mike van Riel",
"email": "[email protected]"
},
{
"name": "Jaap van Otterdijk",
"email": "[email protected]"
}
],
"require": {
"php": ">=5.3.2",
"dflydev/markdown": "1.0.*"
"php": "^7.4 || ^8.0",
"phpdocumentor/type-resolver": "^2.0",
"webmozart/assert": "^1.9.1 || ^2",
"phpdocumentor/reflection-common": "^2.2",
"ext-filter": "*",
"phpstan/phpdoc-parser": "^2.0",
"doctrine/deprecations": "^1.1"
},
"require-dev": {
"mockery/mockery": "~1.3.5 || ~1.6.0",
"phpunit/phpunit": "^9.5",
"phpstan/phpstan": "^1.8",
"phpstan/phpstan-mockery": "^1.1",
"phpstan/extension-installer": "^1.1",
"phpstan/phpstan-webmozart-assert": "^1.2",
"psalm/phar": "^5.26",
"shipmonk/dead-code-detector": "^0.5.1"
},
"autoload": {
"psr-0": {"phpDocumentor\\Reflection": "src/"}
"psr-4": {
"phpDocumentor\\Reflection\\": "src"
}
},
"autoload-dev": {
"psr-4": {
"phpDocumentor\\Reflection\\": ["tests/unit", "tests/integration"]
}
},
"config": {
"platform": {
"php":"7.4.0"
},
"allow-plugins": {
"phpstan/extension-installer": true
}
},
"extra": {
"branch-alias": {
"dev-master": "5.x-dev"
}
}
}
}
Generated
+2527
View File
File diff suppressed because it is too large Load Diff
+12
View File
@@ -0,0 +1,12 @@
Contributing
============
Contributions are welcome! If you would like to contribute to ReflectionDocBlock, please follow these guidelines:
- Fork the repository and create your branch from ``main``.
- Ensure your code follows the project's coding standards.
- Write tests for your changes.
- Submit a pull request with a clear description of your changes.
For questions or discussions, please open an issue on GitHub.
@@ -0,0 +1,27 @@
<?php
require_once(__DIR__ . '/../../vendor/autoload.php');
use phpDocumentor\Reflection\DocBlockFactory;
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* This is a Description. A Summary and Description are separated by either
* two subsequent newlines (thus a whiteline in between as can be seen in this
* example), or when the Summary ends with a dot (`.`) and some form of
* whitespace.
*/
DOCCOMMENT;
$factory = DocBlockFactory::createInstance();
$docblock = $factory->create($docComment);
// Should contain the first line of the DocBlock
$summary = $docblock->getSummary();
// Contains an object of type Description; you can either cast it to string or use
// the render method to get a string representation of the Description.
//
// In subsequent examples we will be fiddling a bit more with the Description.
$description = $docblock->getDescription();
+24
View File
@@ -0,0 +1,24 @@
<?php
require_once(__DIR__ . '/../../vendor/autoload.php');
use phpDocumentor\Reflection\DocBlockFactory;
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* @see \phpDocumentor\Reflection\DocBlock\StandardTagFactory
*/
DOCCOMMENT;
$factory = DocBlockFactory::createInstance();
$docblock = $factory->create($docComment);
// You can check if a DocBlock has one or more see tags
$hasSeeTag = $docblock->hasTag('see');
// Or we can get a complete list of all tags
$tags = $docblock->getTags();
// But we can also grab all tags of a specific type, such as `see`
$seeTags = $docblock->getTagsByName('see');
@@ -0,0 +1,27 @@
<?php
require_once(__DIR__ . '/../../vendor/autoload.php');
use phpDocumentor\Reflection\DocBlock\Serializer;
use phpDocumentor\Reflection\DocBlockFactory;
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* And here is an example of the description
* of a DocBlock that can span multiple lines.
*
* @see \phpDocumentor\Reflection\DocBlock\StandardTagFactory
*/
DOCCOMMENT;
$factory = DocBlockFactory::createInstance();
$docblock = $factory->create($docComment);
// Create the serializer that will reconstitute the DocBlock back to its original form.
$serializer = new Serializer(0, '', true, null, null, PHP_EOL);
// Reconstitution is performed by the `getDocComment()` method.
$reconstitutedDocComment = $serializer->getDocComment($docblock);
+131
View File
@@ -0,0 +1,131 @@
<?php
/**
* In this example we demonstrate how you can add your own Tag using a Static Factory method in your Tag class.
*/
require_once(__DIR__ . '/../../vendor/autoload.php');
use phpDocumentor\Reflection\DocBlock\Serializer;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlockFactory;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tags\BaseTag;
use phpDocumentor\Reflection\Types\Context;
use Webmozart\Assert\Assert;
/**
* An example of a custom tag called `my-tag` with an optional description.
*
* A Custom Tag is a class that can consist of two parts:
*
* 1. a method `create` that is a static factory for this class.
* 2. methods and properties that have this object act as an immutable Value Object representing a Tag instance.
*
* The static factory `create` is used to convert a tag line (without the tag name) into an instance of the
* same tag object with the right constructor parameters set. This method has a dynamic list of parameters so that you
* can inject various dependencies, see the method's DocBlock for more information.
*
* An object of this class, and its methods and properties, represent a single instance of that tag in your
* documentation in the form of a Value Object whose properties should not be changed after instantiation (it should be
* immutable).
*
* > Important: Tag classes that act as Factories using the `create` method should implement the Tag interface.
* > Instead, you could extend the abstract class BaseTag that already implements the Tag interface
*/
final class MyTag extends BaseTag
{
/**
* A required property that is used by Formatters to reconstitute the complete tag line.
*
* @see Formatter
*
* @var string
*/
protected string $name = 'my-tag';
/**
* The constructor for this Tag; this should contain all properties for this object.
*
* @param Description $description An example of how to add a Description to the tag; the Description is often
* an optional variable so passing null is allowed in this instance (though you can
* also construct an empty description object).
*
* @see BaseTag for the declaration of the description property and getDescription method.
*/
public function __construct(Description $description = null)
{
$this->description = $description;
}
/**
* A static Factory that creates a new instance of the current Tag.
*
* In this example the MyTag tag can be created by passing a description text as $body. Because we have added
* a $descriptionFactory that is type-hinted as DescriptionFactory we can now construct a new Description object
* and pass that to the constructor.
*
* > You could directly instantiate a Description object here but that won't be parsed for inline tags and Types
* > won't be resolved. The DescriptionFactory will take care of those actions.
*
* The `create` method's interface states that this method only features a single parameter (`$body`) but the
* {@see TagFactory} will read the signature of this method and if it has more parameters then it will try
* to find declarations for it in the ServiceLocator of the TagFactory (see {@see TagFactory::$serviceLocator}).
*
* > Important: all properties following the `$body` should default to `null`, otherwise PHP will error because
* > it no longer matches the interface. This is why you often see the default tags check that an optional argument
* > is not null nonetheless.
*
* @param string $body
* @param DescriptionFactory $descriptionFactory
* @param Context|null $context The Context is used to resolve Types and FQSENs, although optional
* it is highly recommended to pass it. If you omit it then it is assumed that
* the DocBlock is in the global namespace and has no `use` statements.
*
* @see Tag for the interface declaration of the `create` method.
* @see Tag::create() for more information on this method's workings.
*/
public static function create(string $body, DescriptionFactory $descriptionFactory = null, Context $context = null): self
{
Assert::notNull($descriptionFactory);
return new static($descriptionFactory->create($body, $context));
}
/**
* Returns a rendition of the original tag line.
*
* This method is used to reconstitute a DocBlock into its original form by the {@see Serializer}. It should
* feature all parts of the tag so that the serializer can put it back together.
*/
public function __toString(): string
{
return (string)$this->description;
}
}
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* @my-tag I have a description
*/
DOCCOMMENT;
// Make a mapping between the tag name `my-tag` and the Tag class containing the Factory Method `create`.
$customTags = ['my-tag' => MyTag::class];
// Do pass the list of custom tags to the Factory for the DocBlockFactory.
$factory = DocBlockFactory::createInstance($customTags);
// You can also add Tags later using `$factory->registerTagHandler()` with a tag name and Tag class name.
// Create the DocBlock
$docblock = $factory->create($docComment);
// Take a look: the $customTagObjects now contain an array with your newly added tag
$customTagObjects = $docblock->getTagsByName('my-tag');
// As an experiment: let's reconstitute the DocBlock and observe that because we added a __toString() method
// to the tag class that we can now also see it.
$serializer = new Serializer(0, '',true, null, null, PHP_EOL);
$reconstitutedDocComment = $serializer->getDocComment($docblock);
@@ -0,0 +1,47 @@
<?php
require_once(__DIR__ . '/../../../vendor/autoload.php');
use phpDocumentor\Reflection\DocBlockFactory;
$docComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* You can escape the @-sign by surrounding it with braces, for example: {@}. And escape a closing brace within an
* inline tag by adding an opening brace in front of it like this: {}.
*
* Here are example texts where you can see how they could be used in a real life situation:
*
* This is a text with an {@internal inline tag where a closing brace ({}) is shown}.
* Or an {@internal inline tag with a literal {{@}link{} in it}.
*
* Do note that an {@internal inline tag that has an opening brace ({) does not break out}.
*/
DOCCOMMENT;
$factory = DocBlockFactory::createInstance();
$docblock = $factory->create($docComment);
// Escaping is automatic so this happens in the DescriptionFactory.
$description = $docblock->getDescription();
// This is the rendition that we will receive of the Description.
$receivedDocComment = <<<DOCCOMMENT
/**
* This is an example of a summary.
*
* You can escape the @-sign by surrounding it with braces, for example: {@}. And escape a closing brace within an
* inline tag by adding an opening brace in front of it like this: {}.
*
* Here are example texts where you can see how they could be used in a real life situation:
*
* This is a text with an {@internal inline tag where a closing brace ({}) is shown}.
* Or an {@internal inline tag with a literal {{@}link{} in it}.
*
* Do note that an {@internal inline tag that has an opening brace ({) does not break out}.
*/
DOCCOMMENT;
// Render it using the default PassthroughFormatter
$foundDescription = $description->render();
+9
View File
@@ -0,0 +1,9 @@
Add Your Own Tag
=======================
This guide demonstrates how to add your own custom tag to a DocBlock using ReflectionDocBlock.
.. literalinclude:: ../examples/04-adding-your-own-tag.php
:language: php
:linenos:
+13
View File
@@ -0,0 +1,13 @@
How-to
=============
Practical guides for common tasks with ReflectionDocBlock:
.. toctree::
:maxdepth: 1
interpreting-a-simple-docblock
interpreting-tags
reconstituting-a-docblock
adding-your-own-tag
@@ -0,0 +1,9 @@
Interpret a Simple DocBlock
==================================
This guide demonstrates how to parse a simple DocBlock and extract its summary and description using ReflectionDocBlock.
.. literalinclude:: ../examples/01-interpreting-a-simple-docblock.php
:language: php
:linenos:
+9
View File
@@ -0,0 +1,9 @@
Interpret Tags in a DocBlock
===================================
This guide demonstrates how to interpret tags within a DocBlock using ReflectionDocBlock.
.. literalinclude:: ../examples/02-interpreting-tags.php
:language: php
:linenos:
+10
View File
@@ -0,0 +1,10 @@
Reconstituting a DocBlock
=========================
ReflectionDocBlock not only allows you to read and parse DocBlocks, but also to reconstruct them. This is useful if you need to add, remove, or modify tags in your codebase programmatically. For example, you might want to update type information, add custom tags, or strip deprecated tags as part of a refactoring or code generation process.
Below is a practical example of how to reconstitute a DocBlock using this library:
.. literalinclude:: ../examples/03-reconstituting-a-docblock.php
:language: php
:caption: examples/03-reconstituting-a-docblock.php
+37
View File
@@ -0,0 +1,37 @@
ReflectionDocBlock Documentation
===========================================
ReflectionDocBlock is a PHP library that provides a DocBlock parser fully compatible with the PHPDoc standard. It allows you to parse, interpret, and extract information from DocBlocks in your PHP code, enabling support for annotations and metadata extraction.
Key Features and Use Cases
--------------------------
- **Documentation Generation**: Used as a core component in tools like phpDocumentor to generate API documentation from your code's DocBlocks.
- **Type and Metadata Extraction**: Integrations and tools use this library to gather type information and other metadata, enabling advanced features such as static analysis, code introspection, and automated serialization.
- **Serializer Support**: Helps serializers and similar tools to interpret type information in array and object structures, making it easier to transform nested objects correctly.
- **DocBlock Reconstitution**: Not only can you read DocBlocks, but you can also reconstruct them. This is useful for adding, removing, or modifying tags in your codebase programmatically.
- **Standalone or Integrated**: Designed for standalone use, but also serves as a key component of the phpDocumentor suite.
Unique Advantages
-----------------
- **Simple, Intuitive API**: Focus on ease of use, so you can work with DocBlocks without needing to understand the complexities of parsing.
- **Widely Adopted**: Used by over 1000 packages on Packagist, making it a proven and reliable choice for PHP developers.
- **Actively Maintained**: Supports PHP 7.4 and 8+, and is maintained by the phpDocumentor team and contributors.
Quick Start Example
-------------------
Here's a minimal example of how to use ReflectionDocBlock in your project:
.. literalinclude:: examples/01-interpreting-a-simple-docblock.php
:language: php
:caption: examples/01-interpreting-a-simple-docblock.php
For more detailed usage and how-to guides, see the ``how-to/`` section.
.. toctree::
:maxdepth: 2
:hidden:
installation
how-to/index
upgrade-to-v6
contributing
+9
View File
@@ -0,0 +1,9 @@
Installation
============
To install ReflectionDocBlock, use Composer:
.. code-block:: bash
composer require phpdocumentor/reflection-docblock
+51
View File
@@ -0,0 +1,51 @@
Upgrade Guide to v6
===================
This guide helps you upgrade your project to ReflectionDocBlock v6. It covers breaking changes, removals, new features, and migration tips to ensure a smooth transition.
Supported PHP Versions
----------------------
- v6 requires PHP 7.4 or higher (PHP 8+ recommended).
Breaking Changes & Removals
---------------------------
- **Removal of `::create` static method for type-based tags**
- The `create` static method has been removed from tag classes that represent type definitions, such as `@param` and `@return` tags. Most users will not be affected, as these methods are rarely used directly. The deprecation notice for these methods was present throughout v5.
- **Migration:**
- If you are instantiating these tag objects directly, use the tag factory or the recommended construction pattern instead.
- Before:
.. code-block:: php
$tag = Param::create($body);
- After:
.. code-block:: php
$factory = \phpDocumentor\Reflection\DocBlock\Tags\Factory\StandardTagFactory::createInstance();
$tag = $factory->create('@param int $foo');
- **StandardTagFactory instantiation**
- `StandardTagFactory` must now be created via `createInstance()`.
- **Migration:**
- Before:
.. code-block:: php
$factory = new StandardTagFactory();
- After:
.. code-block:: php
$factory = StandardTagFactory::createInstance();
- **Removed methods**
- `Method::getArguments` has been removed.
- `Method::create` has been removed.
- **Migration:**
- Refactor code to use the new API for method arguments and creation.
TypeResolver Upgrade
-------------------
- **Generics Support**: The TypeResolver component now supports generics,
which replaces the previous `Collection` type handling. This allows
for more accurate and expressive type definitions, such as `MyClass<int, MyClass>` or `Collection<MyClass>`,
and improves compatibility with modern PHPDoc standards.
- For more details and advanced migration scenarios, consult the `TypeResolver upgrade guide <https://docs.phpdoc.org/components/type-resolver/guides/upgrade-v1-to-v2.html#upgrade-to-version-2>`_
+4
View File
@@ -0,0 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<phive xmlns="https://phar.io/phive">
<phar name="phpunit" version="^9.5" installed="9.5.8" location="./tools/phpunit" copy="true"/>
</phive>
+22
View File
@@ -0,0 +1,22 @@
<?xml version="1.0"?>
<ruleset name="ReflectionDocBlock">
<description>The coding standard for this library.</description>
<file>src</file>
<file>tests/unit</file>
<exclude-pattern>*/tests/unit/Types/ContextFactoryTest\.php</exclude-pattern>
<exclude-pattern>*/tests/unit/Assets/*</exclude-pattern>
<arg value="p"/>
<!-- Set the minimum PHP version for PHPCompatibility.
This should be kept in sync with the requirements in the composer.json file. -->
<config name="testVersion" value="7.4-"/>
<rule ref="phpDocumentor">
<exclude name="SlevomatCodingStandard.Exceptions.ReferenceThrowableOnly.ReferencedGeneralException" />
</rule>
<rule ref="SlevomatCodingStandard.Classes.SuperfluousAbstractClassNaming.SuperfluousPrefix">
<exclude-pattern>*/src/*/Abstract*\.php</exclude-pattern>
</rule>
</ruleset>
+46
View File
@@ -0,0 +1,46 @@
<?xml version="1.0" encoding="UTF-8" ?>
<phpdocumentor
configVersion="3"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="https://www.phpdoc.org"
xsi:noNamespaceSchemaLocation="data/xsd/phpdoc.xsd"
>
<title>Reflection Docblock</title>
<paths>
<output>build/docs</output>
</paths>
<version number="6.0.0">
<folder>latest</folder>
<api>
<source dsn="./">
<path>src/</path>
</source>
<output>api</output>
<ignore hidden="true" symlinks="true">
<path>tests/**/*</path>
<path>build/**/*</path>
<path>var/**/*</path>
<path>vendor/**/*</path>
</ignore>
<extensions>
<extension>php</extension>
</extensions>
<ignore-tags>
<ignore-tag>template</ignore-tag>
<ignore-tag>template-extends</ignore-tag>
<ignore-tag>template-implements</ignore-tag>
<ignore-tag>extends</ignore-tag>
<ignore-tag>implements</ignore-tag>
</ignore-tags>
<default-package-name>phpDocumentor</default-package-name>
</api>
<guide>
<source dsn=".">
<path>docs</path>
</source>
<output>guides</output>
</guide>
</version>
<setting name="guides.enabled" value="true"/>
<template name="default" />
</phpdocumentor>
+23
View File
@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8" ?>
<ruleset
name="ProxyManager rules"
xmlns="http://pmd.sf.net/ruleset/1.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://pmd.sf.net/ruleset/1.0.0 http://pmd.sf.net/ruleset_xml_schema.xsd"
xsi:noNamespaceSchemaLocation="http://pmd.sf.net/ruleset_xml_schema.xsd"
>
<rule ref="rulesets/codesize.xml"/>
<rule ref="rulesets/unusedcode.xml"/>
<rule ref="rulesets/design.xml">
<!-- eval is needed to generate runtime classes -->
<exclude name="EvalExpression"/>
</rule>
<rule ref="rulesets/naming.xml">
<exclude name="LongVariable"/>
</rule>
<rule ref="rulesets/naming.xml/LongVariable">
<properties>
<property name="minimum">40</property>
</properties>
</rule>
</ruleset>
+21
View File
@@ -0,0 +1,21 @@
parameters:
ignoreErrors:
-
message: "#^Unused phpDocumentor\\\\Reflection\\\\DocBlock\\\\ExampleFinder\\:\\:getExampleDirectories$#"
count: 1
path: src/DocBlock/ExampleFinder.php
-
message: "#^Unused phpDocumentor\\\\Reflection\\\\DocBlock\\\\ExampleFinder\\:\\:setExampleDirectories$#"
count: 1
path: src/DocBlock/ExampleFinder.php
-
message: "#^Unused phpDocumentor\\\\Reflection\\\\DocBlock\\\\ExampleFinder\\:\\:setSourceDirectory$#"
count: 1
path: src/DocBlock/ExampleFinder.php
-
message: "#^Unused phpDocumentor\\\\Reflection\\\\DocBlock\\\\Tags\\\\Factory\\\\MethodParameterFactory\\:\\:formatNull$#"
count: 1
path: src/DocBlock/Tags/Factory/MethodParameterFactory.php
+17
View File
@@ -0,0 +1,17 @@
includes:
- phpstan-baseline.neon
parameters:
level: max
ignoreErrors:
- '#Method phpDocumentor\\Reflection\\DocBlock\\StandardTagFactory::createTag\(\) should return phpDocumentor\\Reflection\\DocBlock\\Tag but returns mixed#'
- '#Offset 2 on array\{string, 28, int\} on left side of \?\? always exists and is not nullable\.#'
-
path: src/DocBlockFactoryInterface.php
identifier: shipmonk.deadMethod
-
path: src/DocBlock/TagFactory.php
identifier: shipmonk.deadMethod
paths:
- src
- tests/unit
+19 -4
View File
@@ -1,9 +1,24 @@
<?xml version="1.0" encoding="utf-8"?>
<phpunit colors="true" strict="true">
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/9.3/phpunit.xsd" colors="true" convertDeprecationsToExceptions="false" beStrictAboutOutputDuringTests="false" forceCoversAnnotation="true" verbose="true" bootstrap="vendor/autoload.php">
<coverage>
<include>
<directory suffix=".php">./src/</directory>
</include>
<report>
<clover outputFile="build/logs/clover.xml"/>
<html outputDirectory="build/coverage" lowUpperBound="35" highLowerBound="70"/>
</report>
</coverage>
<testsuites>
<testsuite name="phpDocumentor\Reflection\DocBlock">
<directory>./tests/</directory>
<testsuite name="unit">
<directory>./tests/unit</directory>
</testsuite>
<testsuite name="integration">
<directory>./tests/integration</directory>
</testsuite>
</testsuites>
<logging/>
<listeners>
<listener class="Mockery\Adapter\Phpunit\TestListener" file="vendor/mockery/mockery/library/Mockery/Adapter/Phpunit/TestListener.php"/>
</listeners>
</phpunit>
+79
View File
@@ -0,0 +1,79 @@
<?xml version="1.0"?>
<psalm
errorLevel="2"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="https://getpsalm.org/schema/config"
xsi:schemaLocation="https://getpsalm.org/schema/config file:///composer/vendor/vimeo/psalm/config.xsd"
>
<projectFiles>
<directory name="src" />
<ignoreFiles>
<directory name="vendor" />
</ignoreFiles>
</projectFiles>
<issueHandlers>
<RedundantConditionGivenDocblockType>
<errorLevel type="info">
<!-- Psalm is very strict and believe that because we documented a type, it is redundant to assert it -->
<file name="src/DocBlock/StandardTagFactory.php"/>
</errorLevel>
</RedundantConditionGivenDocblockType>
<PossiblyNullArrayOffset>
<errorLevel type="info">
<!-- Psalm forbid accessing an array with a null offset but it's still working code without notice -->
<file name="src/DocBlock/StandardTagFactory.php"/>
</errorLevel>
</PossiblyNullArrayOffset>
<DeprecatedInterface>
<errorLevel type="info">
<!-- Will be removed in 6.0.0 issues/211 -->
<referencedClass name="phpDocumentor\Reflection\DocBlock\Tags\Factory\StaticMethod"/>
</errorLevel>
</DeprecatedInterface>
<DeprecatedMethod>
<errorLevel type="info">
<!-- Will be removed in 6.0.0 issues/361 -->
<referencedMethod name="phpDocumentor\Reflection\DocBlock\Tags\Param::create"/>
</errorLevel>
</DeprecatedMethod>
<NoInterfaceProperties>
<errorLevel type="info">
<file name="src/DocBlock/Tags/Factory/ParamFactory.php"/>
<file name="src/DocBlock/Tags/Factory/AbstractPHPStanFactory.php"/>
</errorLevel>
</NoInterfaceProperties>
<TooManyArguments>
<errorLevel type="info">
<file name="src/DocBlock/Tags/Factory/AbstractPHPStanFactory.php"/>
</errorLevel>
</TooManyArguments>
<RedundantConditionGivenDocblockType>
<errorLevel type="info">
<!-- Psalm manage to infer a more precise type than PHPStan. notNull assert is needed for PHPStan but
Psalm sees it as redundant -->
<directory name="src/DocBlock/Tags/"/>
</errorLevel>
</RedundantConditionGivenDocblockType>
<ArgumentTypeCoercion>
<errorLevel type="info">
<!-- PHP handles invalid preg_split flags just fine. -->
<file name="src/Utils.php"/>
</errorLevel>
</ArgumentTypeCoercion>
<InvalidArgument>
<errorLevel type="suppress">
<referencedFunction name="PHPStan\PhpDocParser\Parser\PhpDocParser::__construct"/>
<referencedFunction name="PHPStan\PhpDocParser\Parser\TypeParser::__construct"/>
</errorLevel>
</InvalidArgument>
</issueHandlers>
</psalm>
+228
View File
@@ -0,0 +1,228 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\TagWithType;
use Webmozart\Assert\Assert;
final class DocBlock
{
/** @var string The opening line for this docblock. */
private string $summary;
/** @var DocBlock\Description The actual description for this docblock. */
private DocBlock\Description $description;
/** @var Tag[] An array containing all the tags in this docblock; except inline. */
private array $tags = [];
/** @var Types\Context|null Information about the context of this DocBlock. */
private ?Types\Context $context = null;
/** @var Location|null Information about the location of this DocBlock. */
private ?Location $location = null;
/** @var bool Is this DocBlock (the start of) a template? */
private bool $isTemplateStart;
/** @var bool Does this DocBlock signify the end of a DocBlock template? */
private bool $isTemplateEnd;
/**
* @param DocBlock\Tag[] $tags
* @param Types\Context $context The context in which the DocBlock occurs.
* @param Location $location The location within the file that this DocBlock occurs in.
*/
public function __construct(
string $summary = '',
?DocBlock\Description $description = null,
array $tags = [],
?Types\Context $context = null,
?Location $location = null,
bool $isTemplateStart = false,
bool $isTemplateEnd = false
) {
Assert::allIsInstanceOf($tags, Tag::class);
$this->summary = $summary;
$this->description = $description ?: new DocBlock\Description('');
foreach ($tags as $tag) {
$this->addTag($tag);
}
$this->context = $context;
$this->location = $location;
$this->isTemplateEnd = $isTemplateEnd;
$this->isTemplateStart = $isTemplateStart;
}
public function getSummary(): string
{
return $this->summary;
}
public function getDescription(): DocBlock\Description
{
return $this->description;
}
/**
* Returns the current context.
*/
public function getContext(): ?Types\Context
{
return $this->context;
}
/**
* Returns the current location.
*/
public function getLocation(): ?Location
{
return $this->location;
}
/**
* Returns whether this DocBlock is the start of a Template section.
*
* A Docblock may serve as template for a series of subsequent DocBlocks. This is indicated by a special marker
* (`#@+`) that is appended directly after the opening `/**` of a DocBlock.
*
* An example of such an opening is:
*
* ```
* /**#@+
* * My DocBlock
* * /
* ```
*
* The description and tags (not the summary!) are copied onto all subsequent DocBlocks and also applied to all
* elements that follow until another DocBlock is found that contains the closing marker (`#@-`).
*
* @see self::isTemplateEnd() for the check whether a closing marker was provided.
*/
public function isTemplateStart(): bool
{
return $this->isTemplateStart;
}
/**
* Returns whether this DocBlock is the end of a Template section.
*
* @see self::isTemplateStart() for a more complete description of the Docblock Template functionality.
*/
public function isTemplateEnd(): bool
{
return $this->isTemplateEnd;
}
/**
* Returns the tags for this DocBlock.
*
* @return Tag[]
*/
public function getTags(): array
{
return $this->tags;
}
/**
* Returns an array of tags matching the given name. If no tags are found
* an empty array is returned.
*
* @param string $name String to search by.
*
* @return Tag[]
*/
public function getTagsByName(string $name): array
{
$result = [];
foreach ($this->getTags() as $tag) {
if ($tag->getName() !== $name) {
continue;
}
$result[] = $tag;
}
return $result;
}
/**
* Returns an array of tags with type matching the given name. If no tags are found
* an empty array is returned.
*
* @param string $name String to search by.
*
* @return TagWithType[]
*/
public function getTagsWithTypeByName(string $name): array
{
$result = [];
foreach ($this->getTagsByName($name) as $tag) {
if (!$tag instanceof TagWithType) {
continue;
}
$result[] = $tag;
}
return $result;
}
/**
* Checks if a tag of a certain type is present in this DocBlock.
*
* @param string $name Tag name to check for.
*/
public function hasTag(string $name): bool
{
foreach ($this->getTags() as $tag) {
if ($tag->getName() === $name) {
return true;
}
}
return false;
}
/**
* Remove a tag from this DocBlock.
*
* @param Tag $tagToRemove The tag to remove.
*/
public function removeTag(Tag $tagToRemove): void
{
foreach ($this->tags as $key => $tag) {
if ($tag === $tagToRemove) {
unset($this->tags[$key]);
break;
}
}
}
/**
* Adds a tag to this DocBlock.
*
* @param Tag $tag The tag to add.
*/
private function addTag(Tag $tag): void
{
$this->tags[] = $tag;
}
}
+118
View File
@@ -0,0 +1,118 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter\PassthroughFormatter;
use function vsprintf;
/**
* Object representing to description for a DocBlock.
*
* A Description object can consist of plain text but can also include tags. A Description Formatter can then combine
* a body template with sprintf-style placeholders together with formatted tags in order to reconstitute a complete
* description text using the format that you would prefer.
*
* Because parsing a Description text can be a verbose process this is handled by the {@see DescriptionFactory}. It is
* thus recommended to use that to create a Description object, like this:
*
* $description = $descriptionFactory->create('This is a {@see Description}', $context);
*
* The description factory will interpret the given body and create a body template and list of tags from them, and pass
* that onto the constructor if this class.
*
* > The $context variable is a class of type {@see \phpDocumentor\Reflection\Types\Context} and contains the namespace
* > and the namespace aliases that apply to this DocBlock. These are used by the Factory to resolve and expand partial
* > type names and FQSENs.
*
* If you do not want to use the DescriptionFactory you can pass a body template and tag listing like this:
*
* $description = new Description(
* 'This is a %1$s',
* [ new See(new Fqsen('\phpDocumentor\Reflection\DocBlock\Description')) ]
* );
*
* It is generally recommended to use the Factory as that will also apply escaping rules, while the Description object
* is mainly responsible for rendering.
*
* @see DescriptionFactory to create a new Description.
* @see Tags\Formatter for the formatting of the body and tags.
*/
class Description
{
private string $bodyTemplate;
/** @var Tag[] */
private array $tags;
/**
* Initializes a Description with its body (template) and a listing of the tags used in the body template.
*
* @param Tag[] $tags
*/
public function __construct(string $bodyTemplate, array $tags = [])
{
$this->bodyTemplate = $bodyTemplate;
$this->tags = $tags;
}
/**
* Returns the body template.
*/
public function getBodyTemplate(): string
{
return $this->bodyTemplate;
}
/**
* Returns the tags for this DocBlock.
*
* @return Tag[]
*/
public function getTags(): array
{
return $this->tags;
}
/**
* Renders this description as a string where the provided formatter will format the tags in the expected string
* format.
*/
public function render(?Formatter $formatter = null): string
{
if ($this->tags === []) {
return vsprintf($this->bodyTemplate, []);
}
if ($formatter === null) {
$formatter = new PassthroughFormatter();
}
$tags = [];
foreach ($this->tags as $tag) {
$tags[] = '{' . $formatter->format($tag) . '}';
}
return vsprintf($this->bodyTemplate, $tags);
}
/**
* Returns a plain string representation of this description.
*/
public function __toString(): string
{
return $this->render();
}
}
+178
View File
@@ -0,0 +1,178 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\Factory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use phpDocumentor\Reflection\Utils;
use function count;
use function implode;
use function ltrim;
use function min;
use function str_replace;
use function strlen;
use function strpos;
use function substr;
use function trim;
use const PREG_SPLIT_DELIM_CAPTURE;
/**
* Creates a new Description object given a body of text.
*
* Descriptions in phpDocumentor are somewhat complex entities as they can contain one or more tags inside their
* body that can be replaced with a readable output. The replacing is done by passing a Formatter object to the
* Description object's `render` method.
*
* In addition to the above does a Description support two types of escape sequences:
*
* 1. `{@}` to escape the `@` character to prevent it from being interpreted as part of a tag, i.e. `{{@}link}`
* 2. `{}` to escape the `}` character, this can be used if you want to use the `}` character in the description
* of an inline tag.
*
* If a body consists of multiple lines then this factory will also remove any superfluous whitespace at the beginning
* of each line while maintaining any indentation that is used. This will prevent formatting parsers from tripping
* over unexpected spaces as can be observed with tag descriptions.
*/
class DescriptionFactory
{
private Factory $tagFactory;
/**
* Initializes this factory with the means to construct (inline) tags.
*/
public function __construct(Factory $tagFactory)
{
$this->tagFactory = $tagFactory;
}
/**
* Returns the parsed text of this description.
*/
public function create(string $contents, ?TypeContext $context = null): Description
{
$tokens = $this->lex($contents);
$count = count($tokens);
$tagCount = 0;
$tags = [];
for ($i = 1; $i < $count; $i += 2) {
$tags[] = $this->tagFactory->create($tokens[$i], $context);
$tokens[$i] = '%' . ++$tagCount . '$s';
}
//In order to allow "literal" inline tags, the otherwise invalid
//sequence "{@}" is changed to "@", and "{}" is changed to "}".
//"%" is escaped to "%%" because of vsprintf.
//See unit tests for examples.
for ($i = 0; $i < $count; $i += 2) {
$tokens[$i] = str_replace(['{@}', '{}', '%'], ['@', '}', '%%'], $tokens[$i]);
}
return new Description(implode('', $tokens), $tags);
}
/**
* Strips the contents from superfluous whitespace and splits the description into a series of tokens.
*
* @return string[] A series of tokens of which the description text is composed.
*/
private function lex(string $contents): array
{
$contents = $this->removeSuperfluousStartingWhitespace($contents);
// performance optimalization; if there is no inline tag, don't bother splitting it up.
if (strpos($contents, '{@') === false) {
return [$contents];
}
return Utils::pregSplit(
'/\{
# "{@}" is not a valid inline tag. This ensures that we do not treat it as one, but treat it literally.
(?!@\})
# We want to capture the whole tag line, but without the inline tag delimiters.
(\@
# Match everything up to the next delimiter.
[^{}]*
# Nested inline tag content should not be captured, or it will appear in the result separately.
(?:
# Match nested inline tags.
(?:
# Because we did not catch the tag delimiters earlier, we must be explicit with them here.
# Notice that this also matches "{}", as a way to later introduce it as an escape sequence.
\{(?1)?\}
|
# Make sure we match hanging "{".
\{
)
# Match content after the nested inline tag.
[^{}]*
)* # If there are more inline tags, match them as well. We use "*" since there may not be any
# nested inline tags.
)
\}/Sux',
$contents,
0,
PREG_SPLIT_DELIM_CAPTURE
);
}
/**
* Removes the superfluous from a multi-line description.
*
* When a description has more than one line then it can happen that the second and subsequent lines have an
* additional indentation. This is commonly in use with tags like this:
*
* {@}since 1.1.0 This is an example
* description where we have an
* indentation in the second and
* subsequent lines.
*
* If we do not normalize the indentation then we have superfluous whitespace on the second and subsequent
* lines and this may cause rendering issues when, for example, using a Markdown converter.
*/
private function removeSuperfluousStartingWhitespace(string $contents): string
{
$lines = Utils::pregSplit("/\r\n?|\n/", $contents);
// if there is only one line then we don't have lines with superfluous whitespace and
// can use the contents as-is
if (count($lines) <= 1) {
return $contents;
}
// determine how many whitespace characters need to be stripped
$startingSpaceCount = 9999999;
for ($i = 1, $iMax = count($lines); $i < $iMax; ++$i) {
// lines with a no length do not count as they are not indented at all
if (trim($lines[$i]) === '') {
continue;
}
// determine the number of prefixing spaces by checking the difference in line length before and after
// an ltrim
$startingSpaceCount = min($startingSpaceCount, strlen($lines[$i]) - strlen(ltrim($lines[$i])));
}
// strip the number of spaces from each line
if ($startingSpaceCount > 0) {
for ($i = 1, $iMax = count($lines); $i < $iMax; ++$i) {
$lines[$i] = substr($lines[$i], $startingSpaceCount);
}
}
return implode("\n", $lines);
}
}
+158
View File
@@ -0,0 +1,158 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Tags\Example;
use function array_slice;
use function file;
use function getcwd;
use function implode;
use function is_readable;
use function rtrim;
use function sprintf;
use function trim;
use const DIRECTORY_SEPARATOR;
/**
* Class used to find an example file's location based on a given ExampleDescriptor.
*/
class ExampleFinder
{
private string $sourceDirectory = '';
/** @var string[] */
private array $exampleDirectories = [];
/**
* Attempts to find the example contents for the given descriptor.
*/
public function find(Example $example): string
{
$filename = $example->getFilePath();
$file = $this->getExampleFileContents($filename);
if ($file === null) {
return sprintf('** File not found : %s **', $filename);
}
return implode('', array_slice($file, $example->getStartingLine() - 1, $example->getLineCount()));
}
/**
* Registers the project's root directory where an 'examples' folder can be expected.
*/
public function setSourceDirectory(string $directory = ''): void
{
$this->sourceDirectory = $directory;
}
/**
* Returns the project's root directory where an 'examples' folder can be expected.
*/
public function getSourceDirectory(): string
{
return $this->sourceDirectory;
}
/**
* Registers a series of directories that may contain examples.
*
* @param string[] $directories
*/
public function setExampleDirectories(array $directories): void
{
$this->exampleDirectories = $directories;
}
/**
* Returns a series of directories that may contain examples.
*
* @return string[]
*/
public function getExampleDirectories(): array
{
return $this->exampleDirectories;
}
/**
* Attempts to find the requested example file and returns its contents or null if no file was found.
*
* This method will try several methods in search of the given example file, the first one it encounters is
* returned:
*
* 1. Iterates through all examples folders for the given filename
* 2. Checks the source folder for the given filename
* 3. Checks the 'examples' folder in the current working directory for examples
* 4. Checks the path relative to the current working directory for the given filename
*
* @return string[] all lines of the example file
*/
private function getExampleFileContents(string $filename): ?array
{
$normalizedPath = null;
foreach ($this->exampleDirectories as $directory) {
$exampleFileFromConfig = $this->constructExamplePath($directory, $filename);
if (is_readable($exampleFileFromConfig)) {
$normalizedPath = $exampleFileFromConfig;
break;
}
}
if ($normalizedPath === null) {
if (is_readable($this->getExamplePathFromSource($filename))) {
$normalizedPath = $this->getExamplePathFromSource($filename);
} elseif (is_readable($this->getExamplePathFromExampleDirectory($filename))) {
$normalizedPath = $this->getExamplePathFromExampleDirectory($filename);
} elseif (is_readable($filename)) {
$normalizedPath = $filename;
}
}
$lines = $normalizedPath !== null && is_readable($normalizedPath) ? file($normalizedPath) : false;
return $lines !== false ? $lines : null;
}
/**
* Get example filepath based on the example directory inside your project.
*/
private function getExamplePathFromExampleDirectory(string $file): string
{
return getcwd() . DIRECTORY_SEPARATOR . 'examples' . DIRECTORY_SEPARATOR . $file;
}
/**
* Returns a path to the example file in the given directory..
*/
private function constructExamplePath(string $directory, string $file): string
{
return rtrim($directory, '\\/') . DIRECTORY_SEPARATOR . $file;
}
/**
* Get example filepath based on sourcecode.
*/
private function getExamplePathFromSource(string $file): string
{
return sprintf(
'%s%s%s',
trim($this->getSourceDirectory(), '\\/'),
DIRECTORY_SEPARATOR,
trim($file, '"')
);
}
}
+156
View File
@@ -0,0 +1,156 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter\PassthroughFormatter;
use function sprintf;
use function str_repeat;
use function str_replace;
use function strlen;
use function wordwrap;
/**
* Converts a DocBlock back from an object to a complete DocComment including Asterisks.
*/
class Serializer
{
/** @var string The string to indent the comment with. */
protected string $indentString = ' ';
/** @var int The number of times the indent string is repeated. */
protected int $indent = 0;
/** @var bool Whether to indent the first line with the given indent amount and string. */
protected bool $isFirstLineIndented = true;
/** @var int|null The max length of a line. */
protected ?int $lineLength = null;
/** @var Formatter A custom tag formatter. */
protected Formatter $tagFormatter;
private string $lineEnding;
/**
* Create a Serializer instance.
*
* @param int $indent The number of times the indent string is repeated.
* @param string $indentString The string to indent the comment with.
* @param bool $indentFirstLine Whether to indent the first line.
* @param int|null $lineLength The max length of a line or NULL to disable line wrapping.
* @param Formatter $tagFormatter A custom tag formatter, defaults to PassthroughFormatter.
* @param string $lineEnding Line ending used in the output, by default \n is used.
*/
public function __construct(
int $indent = 0,
string $indentString = ' ',
bool $indentFirstLine = true,
?int $lineLength = null,
?Formatter $tagFormatter = null,
string $lineEnding = "\n"
) {
$this->indent = $indent;
$this->indentString = $indentString;
$this->isFirstLineIndented = $indentFirstLine;
$this->lineLength = $lineLength;
$this->tagFormatter = $tagFormatter ?: new PassthroughFormatter();
$this->lineEnding = $lineEnding;
}
/**
* Generate a DocBlock comment.
*
* @param DocBlock $docblock The DocBlock to serialize.
*
* @return string The serialized doc block.
*/
public function getDocComment(DocBlock $docblock): string
{
$indent = str_repeat($this->indentString, $this->indent);
$firstIndent = $this->isFirstLineIndented ? $indent : '';
// 3 === strlen(' * ')
$wrapLength = $this->lineLength !== null ? $this->lineLength - strlen($indent) - 3 : null;
$text = $this->removeTrailingSpaces(
$indent,
$this->addAsterisksForEachLine(
$indent,
$this->getSummaryAndDescriptionTextBlock($docblock, $wrapLength)
)
);
$comment = $firstIndent . "/**\n";
if ($text) {
$comment .= $indent . ' * ' . $text . "\n";
$comment .= $indent . " *\n";
}
$comment = $this->addTagBlock($docblock, $wrapLength, $indent, $comment);
return str_replace("\n", $this->lineEnding, $comment . $indent . ' */');
}
private function removeTrailingSpaces(string $indent, string $text): string
{
return str_replace(
sprintf("\n%s * \n", $indent),
sprintf("\n%s *\n", $indent),
$text
);
}
private function addAsterisksForEachLine(string $indent, string $text): string
{
return str_replace(
"\n",
sprintf("\n%s * ", $indent),
$text
);
}
private function getSummaryAndDescriptionTextBlock(DocBlock $docblock, ?int $wrapLength): string
{
$text = $docblock->getSummary() . ((string) $docblock->getDescription() ? "\n\n" . $docblock->getDescription()
: '');
if ($wrapLength !== null) {
$text = wordwrap($text, $wrapLength);
return $text;
}
return $text;
}
private function addTagBlock(DocBlock $docblock, ?int $wrapLength, string $indent, string $comment): string
{
foreach ($docblock->getTags() as $tag) {
$tagText = $this->tagFormatter->format($tag);
if ($wrapLength !== null) {
$tagText = wordwrap($tagText, $wrapLength);
}
$tagText = str_replace(
"\n",
sprintf("\n%s * ", $indent),
$tagText
);
$comment .= sprintf("%s * %s\n", $indent, $tagText);
}
return $comment;
}
}
+392
View File
@@ -0,0 +1,392 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use InvalidArgumentException;
use phpDocumentor\Reflection\DocBlock\Tags\Author;
use phpDocumentor\Reflection\DocBlock\Tags\Covers;
use phpDocumentor\Reflection\DocBlock\Tags\Deprecated;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\AbstractPHPStanFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\ExtendsFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\Factory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\ImplementsFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\MethodFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\MixinFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\ParamFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\PropertyFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\PropertyReadFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\PropertyWriteFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\ReturnFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\TemplateCovariantFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\TemplateFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\ThrowsFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\VarFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Generic;
use phpDocumentor\Reflection\DocBlock\Tags\InvalidTag;
use phpDocumentor\Reflection\DocBlock\Tags\Link as LinkTag;
use phpDocumentor\Reflection\DocBlock\Tags\See as SeeTag;
use phpDocumentor\Reflection\DocBlock\Tags\Since;
use phpDocumentor\Reflection\DocBlock\Tags\Source;
use phpDocumentor\Reflection\DocBlock\Tags\Uses;
use phpDocumentor\Reflection\DocBlock\Tags\Version;
use phpDocumentor\Reflection\FqsenResolver;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use ReflectionMethod;
use ReflectionNamedType;
use ReflectionParameter;
use Webmozart\Assert\Assert;
use function array_key_exists;
use function array_merge;
use function array_slice;
use function call_user_func_array;
use function get_class;
use function is_object;
use function preg_match;
use function sprintf;
use function strpos;
use function trim;
/**
* Creates a Tag object given the contents of a tag.
*
* This Factory is capable of determining the appropriate class for a tag and instantiate it using its `create`
* factory method. The `create` factory method of a Tag can have a variable number of arguments; this way you can
* pass the dependencies that you need to construct a tag object.
*
* > Important: each parameter in addition to the body variable for the `create` method must default to null, otherwise
* > it violates the constraint with the interface; it is recommended to use the {@see Assert::notNull()} method to
* > verify that a dependency is actually passed.
*
* This Factory also features a Service Locator component that is used to pass the right dependencies to the
* `create` method of a tag; each dependency should be registered as a service or as a parameter.
*
* When you want to use a Tag of your own with custom handling you need to call the `registerTagHandler` method, pass
* the name of the tag and a Fully Qualified Class Name pointing to a class that implements the Tag interface.
*/
final class StandardTagFactory implements TagFactory
{
/** PCRE regular expression matching a tag name. */
public const REGEX_TAGNAME = '[\w\-\_\\\\:]+';
/**
* @var array<string, class-string<Tag>|Tag|Factory> An array with a tag as a key, and an
* FQCN to a class that handles it as an array value.
*/
private array $tagHandlerMappings = [
'author' => Author::class,
'covers' => Covers::class,
'deprecated' => Deprecated::class,
'link' => LinkTag::class,
'see' => SeeTag::class,
'since' => Since::class,
'source' => Source::class,
'uses' => Uses::class,
'version' => Version::class,
];
/**
* @var array<class-string<Tag>> An array with an annotation as a key, and an
* FQCN to a class that handles it as an array value.
*/
private array $annotationMappings = [];
/**
* @var ReflectionParameter[][] a lazy-loading cache containing parameters
* for each tagHandler that has been used.
*/
private array $tagHandlerParameterCache = [];
private FqsenResolver $fqsenResolver;
/**
* @var mixed[] an array representing a simple Service Locator where we can store parameters and
* services that can be inserted into the Factory Methods of Tag Handlers.
*/
private array $serviceLocator = [];
private function __construct(FqsenResolver $fqsenResolver)
{
$this->fqsenResolver = $fqsenResolver;
$this->addService($fqsenResolver, FqsenResolver::class);
}
/**
* Initialize this tag factory with the means to resolve an FQSEN.
*
* @see self::registerTagHandler() to add a new tag handler to the existing default list.
*/
public static function createInstance(FqsenResolver $fqsenResolver): self
{
$tagFactory = new self($fqsenResolver);
$descriptionFactory = new DescriptionFactory($tagFactory);
$typeResolver = new TypeResolver($fqsenResolver);
$phpstanTagFactory = new AbstractPHPStanFactory(
new ParamFactory($typeResolver, $descriptionFactory),
new VarFactory($typeResolver, $descriptionFactory),
new ReturnFactory($typeResolver, $descriptionFactory),
new PropertyFactory($typeResolver, $descriptionFactory),
new PropertyReadFactory($typeResolver, $descriptionFactory),
new PropertyWriteFactory($typeResolver, $descriptionFactory),
new MethodFactory($typeResolver, $descriptionFactory),
new MixinFactory($typeResolver, $descriptionFactory),
new ImplementsFactory($typeResolver, $descriptionFactory),
new ExtendsFactory($typeResolver, $descriptionFactory),
new TemplateFactory($typeResolver, $descriptionFactory),
new TemplateCovariantFactory($typeResolver, $descriptionFactory),
new ThrowsFactory($typeResolver, $descriptionFactory),
);
$tagFactory->addService($descriptionFactory);
$tagFactory->addService($typeResolver);
$tagFactory->registerTagHandler('param', $phpstanTagFactory);
$tagFactory->registerTagHandler('var', $phpstanTagFactory);
$tagFactory->registerTagHandler('return', $phpstanTagFactory);
$tagFactory->registerTagHandler('property', $phpstanTagFactory);
$tagFactory->registerTagHandler('property-read', $phpstanTagFactory);
$tagFactory->registerTagHandler('property-write', $phpstanTagFactory);
$tagFactory->registerTagHandler('method', $phpstanTagFactory);
$tagFactory->registerTagHandler('mixin', $phpstanTagFactory);
$tagFactory->registerTagHandler('extends', $phpstanTagFactory);
$tagFactory->registerTagHandler('implements', $phpstanTagFactory);
$tagFactory->registerTagHandler('template', $phpstanTagFactory);
$tagFactory->registerTagHandler('template-covariant', $phpstanTagFactory);
$tagFactory->registerTagHandler('template-extends', $phpstanTagFactory);
$tagFactory->registerTagHandler('template-implements', $phpstanTagFactory);
$tagFactory->registerTagHandler('throws', $phpstanTagFactory);
return $tagFactory;
}
public function create(string $tagLine, ?TypeContext $context = null): Tag
{
if (!$context) {
$context = new TypeContext('');
}
[$tagName, $tagBody] = $this->extractTagParts($tagLine);
return $this->createTag(trim($tagBody), $tagName, $context);
}
/**
* @param mixed $value
*/
public function addParameter(string $name, $value): void
{
$this->serviceLocator[$name] = $value;
}
public function addService(object $service, ?string $alias = null): void
{
$this->serviceLocator[$alias ?? get_class($service)] = $service;
}
/** {@inheritDoc} */
public function registerTagHandler(string $tagName, $handler): void
{
Assert::stringNotEmpty($tagName);
if (strpos($tagName, '\\') !== false && $tagName[0] !== '\\') {
throw new InvalidArgumentException(
'A namespaced tag must have a leading backslash as it must be fully qualified'
);
}
if (is_object($handler)) {
Assert::isInstanceOf($handler, Factory::class);
$this->tagHandlerMappings[$tagName] = $handler;
return;
}
Assert::classExists($handler);
Assert::implementsInterface($handler, Tag::class);
$this->tagHandlerMappings[$tagName] = $handler;
}
/**
* Extracts all components for a tag.
*
* @return string[]
*/
private function extractTagParts(string $tagLine): array
{
$matches = [];
if (!preg_match('/^@(' . self::REGEX_TAGNAME . ')((?:[\s\(\{])\s*([^\s].*)|$)/us', $tagLine, $matches)) {
throw new InvalidArgumentException(
'The tag "' . $tagLine . '" does not seem to be wellformed, please check it for errors'
);
}
return array_slice($matches, 1);
}
/**
* Creates a new tag object with the given name and body or returns null if the tag name was recognized but the
* body was invalid.
*/
private function createTag(string $body, string $name, TypeContext $context): Tag
{
$handlerClassName = $this->findHandlerClassName($name, $context);
$arguments = $this->getArgumentsForParametersFromWiring(
$this->fetchParametersForHandlerFactoryMethod($handlerClassName),
$this->getServiceLocatorWithDynamicParameters($context, $name, $body)
);
if (array_key_exists('tagLine', $arguments)) {
$arguments['tagLine'] = sprintf('@%s %s', $name, $body);
}
try {
$callable = [$handlerClassName, 'create'];
Assert::isCallable($callable);
/** @phpstan-var callable(string): ?Tag $callable */
$tag = call_user_func_array($callable, $arguments);
return $tag ?? InvalidTag::create($body, $name);
} catch (InvalidArgumentException $e) {
return InvalidTag::create($body, $name)->withError($e);
}
}
/**
* Determines the Fully Qualified Class Name of the Factory or Tag (containing a Factory Method `create`).
*
* @return class-string<Tag>|Tag|Factory
*/
private function findHandlerClassName(string $tagName, TypeContext $context)
{
$handlerClassName = Generic::class;
if (isset($this->tagHandlerMappings[$tagName])) {
$handlerClassName = $this->tagHandlerMappings[$tagName];
} elseif ($this->isAnnotation($tagName)) {
// TODO: Annotation support is planned for a later stage and as such is disabled for now
$tagName = (string) $this->fqsenResolver->resolve($tagName, $context);
if (isset($this->annotationMappings[$tagName])) {
$handlerClassName = $this->annotationMappings[$tagName];
}
}
return $handlerClassName;
}
/**
* Retrieves the arguments that need to be passed to the Factory Method with the given Parameters.
*
* @param ReflectionParameter[] $parameters
* @param mixed[] $locator
*
* @return mixed[] A series of values that can be passed to the Factory Method of the tag whose parameters
* is provided with this method.
*/
private function getArgumentsForParametersFromWiring(array $parameters, array $locator): array
{
$arguments = [];
foreach ($parameters as $parameter) {
$type = $parameter->getType();
$typeHint = null;
if ($type instanceof ReflectionNamedType) {
$typeHint = $type->getName();
if ($typeHint === 'self') {
$declaringClass = $parameter->getDeclaringClass();
if ($declaringClass !== null) {
$typeHint = $declaringClass->getName();
}
}
}
$parameterName = $parameter->getName();
if (isset($locator[$typeHint ?? ''])) {
$arguments[$parameterName] = $locator[$typeHint ?? ''];
continue;
}
if (isset($locator[$parameterName])) {
$arguments[$parameterName] = $locator[$parameterName];
continue;
}
$arguments[$parameterName] = null;
}
return $arguments;
}
/**
* Retrieves a series of ReflectionParameter objects for the static 'create' method of the given
* tag handler class name.
*
* @param class-string<Tag>|Tag|Factory $handler
*
* @return ReflectionParameter[]
*/
private function fetchParametersForHandlerFactoryMethod($handler): array
{
$handlerClassName = is_object($handler) ? get_class($handler) : $handler;
if (!isset($this->tagHandlerParameterCache[$handlerClassName])) {
$methodReflection = new ReflectionMethod($handlerClassName, 'create');
$this->tagHandlerParameterCache[$handlerClassName] = $methodReflection->getParameters();
}
return $this->tagHandlerParameterCache[$handlerClassName];
}
/**
* Returns a copy of this class' Service Locator with added dynamic parameters,
* such as the tag's name, body and Context.
*
* @param TypeContext $context The Context (namespace and aliases) that may be
* passed and is used to resolve FQSENs.
* @param string $tagName The name of the tag that may be
* passed onto the factory method of the Tag class.
* @param string $tagBody The body of the tag that may be
* passed onto the factory method of the Tag class.
*
* @return mixed[]
*/
private function getServiceLocatorWithDynamicParameters(
TypeContext $context,
string $tagName,
string $tagBody
): array {
return array_merge(
$this->serviceLocator,
[
'name' => $tagName,
'body' => $tagBody,
TypeContext::class => $context,
]
);
}
/**
* Returns whether the given tag belongs to an annotation.
*
* @todo this method should be populated once we implement Annotation notation support.
*/
private function isAnnotation(string $tagContent): bool
{
// 1. Contains a namespace separator
// 2. Contains parenthesis
// 3. Is present in a list of known annotations (make the algorithm smart by first checking is the last part
// of the annotation class name matches the found tag name
return false;
}
}
+31
View File
@@ -0,0 +1,31 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter;
interface Tag
{
public function getName(): string;
/**
* @return Tag|mixed Class that implements Tag
* @phpstan-return ?Tag
*/
public static function create(string $body);
public function render(?Formatter $formatter = null): string;
public function __toString(): string;
}
+73
View File
@@ -0,0 +1,73 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock;
use InvalidArgumentException;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\Factory;
interface TagFactory extends Factory
{
/**
* Adds a parameter to the service locator that can be injected in a tag's factory method.
*
* When calling a tag's "create" method we always check the signature for dependencies to inject. One way is to
* typehint a parameter in the signature so that we can use that interface or class name to inject a dependency
* (see {@see addService()} for more information on that).
*
* Another way is to check the name of the argument against the names in the Service Locator. With this method
* you can add a variable that will be inserted when a tag's create method is not typehinted and has a matching
* name.
*
* Be aware that there are two reserved names:
*
* - name, representing the name of the tag.
* - body, representing the complete body of the tag.
*
* These parameters are injected at the last moment and will override any existing parameter with those names.
*
* @param mixed $value
*/
public function addParameter(string $name, $value): void;
/**
* Registers a service with the Service Locator using the FQCN of the class or the alias, if provided.
*
* When calling a tag's "create" method we always check the signature for dependencies to inject. If a parameter
* has a typehint then the ServiceLocator is queried to see if a Service is registered for that typehint.
*
* Because interfaces are regularly used as type-hints this method provides an alias parameter; if the FQCN of the
* interface is passed as alias then every time that interface is requested the provided service will be returned.
*/
public function addService(object $service): void;
/**
* Registers a handler for tags.
*
* If you want to use your own tags then you can use this method to instruct the TagFactory
* to register the name of a tag with the FQCN of a 'Tag Handler'. The Tag handler should implement
* the {@see Tag} interface (and thus the create method).
*
* @param string $tagName Name of tag to register a handler for. When registering a namespaced
* tag, the full name, along with a prefixing slash MUST be provided.
* @param class-string<Tag>|Factory $handler FQCN of handler.
*
* @throws InvalidArgumentException If the tag name is not a string.
* @throws InvalidArgumentException If the tag name is namespaced (contains backslashes) but
* does not start with a backslash.
* @throws InvalidArgumentException If the handler is not a string.
* @throws InvalidArgumentException If the handler is not an existing class.
* @throws InvalidArgumentException If the handler does not implement the {@see Tag} interface.
*/
public function registerTagHandler(string $tagName, $handler): void;
}
+102
View File
@@ -0,0 +1,102 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use InvalidArgumentException;
use function filter_var;
use function preg_match;
use function trim;
use const FILTER_VALIDATE_EMAIL;
/**
* Reflection class for an {@}author tag in a Docblock.
*/
final class Author extends BaseTag
{
/** @var string register that this is the author tag. */
protected string $name = 'author';
/** @var string The name of the author */
private string $authorName;
/** @var string The email of the author */
private string $authorEmail;
/**
* Initializes this tag with the author name and e-mail.
*/
public function __construct(string $authorName, string $authorEmail)
{
if ($authorEmail && !filter_var($authorEmail, FILTER_VALIDATE_EMAIL)) {
throw new InvalidArgumentException('The author tag does not have a valid e-mail address');
}
$this->authorName = $authorName;
$this->authorEmail = $authorEmail;
}
/**
* Gets the author's name.
*
* @return string The author's name.
*/
public function getAuthorName(): string
{
return $this->authorName;
}
/**
* Returns the author's email.
*
* @return string The author's email.
*/
public function getEmail(): string
{
return $this->authorEmail;
}
/**
* Returns this tag in string form.
*/
public function __toString(): string
{
if ($this->authorEmail) {
$authorEmail = '<' . $this->authorEmail . '>';
} else {
$authorEmail = '';
}
$authorName = $this->authorName;
return $authorName . ($authorEmail !== '' ? ($authorName !== '' ? ' ' : '') . $authorEmail : '');
}
/**
* Attempts to create a new Author object based on the tag body.
*/
public static function create(string $body): ?self
{
$splitTagContent = preg_match('/^([^\<]*)(?:\<([^\>]*)\>)?$/u', $body, $matches);
if (!$splitTagContent) {
return null;
}
$authorName = trim($matches[1]);
$email = isset($matches[2]) ? trim($matches[2]) : '';
return new static($authorName, $email);
}
}
+53
View File
@@ -0,0 +1,53 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock;
use phpDocumentor\Reflection\DocBlock\Description;
/**
* Parses a tag definition for a DocBlock.
*/
abstract class BaseTag implements DocBlock\Tag
{
/** @var string Name of the tag */
protected string $name = '';
/** @var Description|null Description of the tag. */
protected ?Description $description = null;
/**
* Gets the name of this tag.
*
* @return string The name of this tag.
*/
public function getName(): string
{
return $this->name;
}
public function getDescription(): ?Description
{
return $this->description;
}
public function render(?Formatter $formatter = null): string
{
if ($formatter === null) {
$formatter = new Formatter\PassthroughFormatter();
}
return $formatter->format($this);
}
}
+99
View File
@@ -0,0 +1,99 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Fqsen;
use phpDocumentor\Reflection\FqsenResolver;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use phpDocumentor\Reflection\Utils;
use Webmozart\Assert\Assert;
use function array_key_exists;
use function explode;
/**
* Reflection class for a @covers tag in a Docblock.
*/
final class Covers extends BaseTag
{
protected string $name = 'covers';
private Fqsen $refers;
/**
* Initializes this tag.
*/
public function __construct(Fqsen $refers, ?Description $description = null)
{
$this->refers = $refers;
$this->description = $description;
}
public static function create(
string $body,
?DescriptionFactory $descriptionFactory = null,
?FqsenResolver $resolver = null,
?TypeContext $context = null
): self {
Assert::stringNotEmpty($body);
Assert::notNull($descriptionFactory);
Assert::notNull($resolver);
$parts = Utils::pregSplit('/\s+/Su', $body, 2);
return new static(
self::resolveFqsen($parts[0], $resolver, $context),
$descriptionFactory->create($parts[1] ?? '', $context)
);
}
private static function resolveFqsen(string $parts, ?FqsenResolver $fqsenResolver, ?TypeContext $context): Fqsen
{
Assert::notNull($fqsenResolver);
$fqsenParts = explode('::', $parts);
$resolved = $fqsenResolver->resolve($fqsenParts[0], $context);
if (!array_key_exists(1, $fqsenParts)) {
return $resolved;
}
return new Fqsen($resolved . '::' . $fqsenParts[1]);
}
/**
* Returns the structural element this tag refers to.
*/
public function getReference(): Fqsen
{
return $this->refers;
}
/**
* Returns a string representation of this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$refers = (string) $this->refers;
return $refers . ($description !== '' ? ($refers !== '' ? ' ' : '') . $description : '');
}
}
+108
View File
@@ -0,0 +1,108 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use Webmozart\Assert\Assert;
use function preg_match;
/**
* Reflection class for a {@}deprecated tag in a Docblock.
*/
final class Deprecated extends BaseTag
{
protected string $name = 'deprecated';
/**
* PCRE regular expression matching a version vector.
* Assumes the "x" modifier.
*/
public const REGEX_VECTOR = '(?:
# Normal release vectors.
\d\S*
|
# VCS version vectors. Per PHPCS, they are expected to
# follow the form of the VCS name, followed by ":", followed
# by the version vector itself.
# By convention, popular VCSes like CVS, SVN and GIT use "$"
# around the actual version vector.
[^\s\:]+\:\s*\$[^\$]+\$
)';
/** @var string|null The version vector. */
private ?string $version = null;
public function __construct(?string $version = null, ?Description $description = null)
{
Assert::nullOrNotEmpty($version);
$this->version = $version;
$this->description = $description;
}
/**
* @return static
*/
public static function create(
?string $body,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
if ($body === null || $body === '') {
return new static();
}
$matches = [];
if (!preg_match('/^(' . self::REGEX_VECTOR . ')\s*(.+)?$/sux', $body, $matches)) {
return new static(
null,
$descriptionFactory !== null ? $descriptionFactory->create($body, $context) : null
);
}
Assert::notNull($descriptionFactory);
return new static(
$matches[1],
$descriptionFactory->create($matches[2] ?? '', $context)
);
}
/**
* Gets the version section of the tag.
*/
public function getVersion(): ?string
{
return $this->version;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$version = (string) $this->version;
return $version . ($description !== '' ? ($version !== '' ? ' ' : '') . $description : '');
}
}
+197
View File
@@ -0,0 +1,197 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Tag;
use Webmozart\Assert\Assert;
use function array_key_exists;
use function preg_match;
use function rawurlencode;
use function str_replace;
use function strpos;
use function trim;
/**
* Reflection class for a {@}example tag in a Docblock.
*/
final class Example implements Tag
{
/** @var string Path to a file to use as an example. May also be an absolute URI. */
private string $filePath;
/**
* @var bool Whether the file path component represents an URI. This determines how the file portion
* appears at {@link getContent()}.
*/
private bool $isURI;
private int $startingLine;
private int $lineCount;
private ?string $content = null;
public function __construct(
string $filePath,
bool $isURI,
int $startingLine,
int $lineCount,
?string $content
) {
Assert::stringNotEmpty($filePath);
Assert::greaterThanEq($startingLine, 1);
Assert::greaterThanEq($lineCount, 0);
$this->filePath = $filePath;
$this->startingLine = $startingLine;
$this->lineCount = $lineCount;
if ($content !== null) {
$this->content = trim($content);
}
$this->isURI = $isURI;
}
public function getContent(): string
{
if ($this->content === null || $this->content === '') {
$filePath = $this->filePath;
if ($this->isURI) {
$filePath = $this->isUriRelative($this->filePath)
? str_replace('%2F', '/', rawurlencode($this->filePath))
: $this->filePath;
}
return trim($filePath);
}
return $this->content;
}
public function getDescription(): ?string
{
return $this->content;
}
public static function create(string $body): ?Tag
{
// File component: File path in quotes or File URI / Source information
if (!preg_match('/^\s*(?:(\"[^\"]+\")|(\S+))(?:\s+(.*))?$/sux', $body, $matches)) {
return null;
}
$filePath = null;
$fileUri = null;
if (array_key_exists(1, $matches) && $matches[1] !== '') {
$filePath = $matches[1];
} else {
$fileUri = array_key_exists(2, $matches) ? $matches[2] : '';
}
$startingLine = 1;
$lineCount = 0;
$description = null;
if (array_key_exists(3, $matches)) {
$description = $matches[3];
// Starting line / Number of lines / Description
if (preg_match('/^([1-9]\d*)(?:\s+((?1))\s*)?(.*)$/sux', $matches[3], $contentMatches)) {
$startingLine = (int) $contentMatches[1];
if (isset($contentMatches[2])) {
$lineCount = (int) $contentMatches[2];
}
if (array_key_exists(3, $contentMatches)) {
$description = $contentMatches[3];
}
}
}
return new static(
$filePath ?? ($fileUri ?? ''),
$fileUri !== null,
$startingLine,
$lineCount,
$description
);
}
/**
* Returns the file path.
*
* @return string Path to a file to use as an example.
* May also be an absolute URI.
*/
public function getFilePath(): string
{
return trim($this->filePath, '"');
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
$filePath = $this->filePath;
$isDefaultLine = $this->startingLine === 1 && $this->lineCount === 0;
$startingLine = !$isDefaultLine ? (string) $this->startingLine : '';
$lineCount = !$isDefaultLine ? (string) $this->lineCount : '';
$content = (string) $this->content;
return $filePath
. ($startingLine !== ''
? ($filePath !== '' ? ' ' : '') . $startingLine
: '')
. ($lineCount !== ''
? ($filePath !== '' || $startingLine !== '' ? ' ' : '') . $lineCount
: '')
. ($content !== ''
? ($filePath !== '' || $startingLine !== '' || $lineCount !== '' ? ' ' : '') . $content
: '');
}
/**
* Returns true if the provided URI is relative or contains a complete scheme (and thus is absolute).
*/
private function isUriRelative(string $uri): bool
{
return strpos($uri, ':') === false;
}
public function getStartingLine(): int
{
return $this->startingLine;
}
public function getLineCount(): int
{
return $this->lineCount;
}
public function getName(): string
{
return 'example';
}
public function render(?Formatter $formatter = null): string
{
if ($formatter === null) {
$formatter = new Formatter\PassthroughFormatter();
}
return $formatter->format($this);
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}extends tag in a Docblock.
*/
class Extends_ extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'extends';
$this->type = $type;
$this->description = $description;
}
}
@@ -0,0 +1,129 @@
<?php
/*
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*
*/
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\InvalidTag;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use PHPStan\PhpDocParser\Lexer\Lexer;
use PHPStan\PhpDocParser\Parser\ConstExprParser;
use PHPStan\PhpDocParser\Parser\ParserException;
use PHPStan\PhpDocParser\Parser\PhpDocParser;
use PHPStan\PhpDocParser\Parser\TokenIterator;
use PHPStan\PhpDocParser\Parser\TypeParser;
use PHPStan\PhpDocParser\ParserConfig;
use RuntimeException;
use function ltrim;
use function property_exists;
use function rtrim;
/**
* Factory class creating tags using phpstan's parser
*
* This class uses {@see PHPStanFactory} implementations to create tags
* from the ast of the phpstan docblock parser.
*
* @internal This class is not part of the BC promise of this library.
*/
class AbstractPHPStanFactory implements Factory
{
private PhpDocParser $parser;
private Lexer $lexer;
/** @var PHPStanFactory[] */
private array $factories;
public function __construct(PHPStanFactory ...$factories)
{
$config = new ParserConfig(['indexes' => true, 'lines' => true]);
$this->lexer = new Lexer($config);
$constParser = new ConstExprParser($config);
$this->parser = new PhpDocParser(
$config,
new TypeParser($config, $constParser),
$constParser
);
$this->factories = $factories;
}
public function create(string $tagLine, ?TypeContext $context = null): Tag
{
try {
$tokens = $this->tokenizeLine($tagLine . "\n");
$ast = $this->parser->parseTag($tokens);
if (property_exists($ast->value, 'description') === true) {
$ast->value->setAttribute(
'description',
rtrim($ast->value->description . $tokens->joinUntil(Lexer::TOKEN_END), "\n")
);
}
} catch (ParserException $e) {
return InvalidTag::create($tagLine, '')->withError($e);
}
if ($context === null) {
$context = new TypeContext('');
}
try {
foreach ($this->factories as $factory) {
if ($factory->supports($ast, $context)) {
return $factory->create($ast, $context);
}
}
} catch (RuntimeException $e) {
return InvalidTag::create((string) $ast->value, 'method')->withError($e);
} catch (ParserException $e) {
return InvalidTag::create((string) $ast->value, $ast->name)->withError($e);
}
return InvalidTag::create(
(string) $ast->value,
$ast->name
);
}
/**
* Solve the issue with the lexer not tokenizing the line correctly
*
* This method is a workaround for the lexer that includes newline tokens with spaces. For
* phpstan this isn't an issue, as it doesn't do a lot of things with the indentation of descriptions.
* But for us is important to keep the indentation of the descriptions, so we need to fix the lexer output.
*/
private function tokenizeLine(string $tagLine): TokenIterator
{
$tokens = $this->lexer->tokenize($tagLine);
$fixed = [];
foreach ($tokens as $token) {
if (($token[1] === Lexer::TOKEN_PHPDOC_EOL) && rtrim($token[0], " \t") !== $token[0]) {
$fixed[] = [
rtrim($token[Lexer::VALUE_OFFSET], " \t"),
Lexer::TOKEN_PHPDOC_EOL,
$token[2] ?? 0,
];
$fixed[] = [
ltrim($token[Lexer::VALUE_OFFSET], "\n\r"),
Lexer::TOKEN_HORIZONTAL_WS,
($token[2] ?? 0) + 1,
];
continue;
}
$fixed[] = $token;
}
return new TokenIterator($fixed);
}
}
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Extends_;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\ExtendsTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class ExtendsFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof ExtendsTagValueNode && $node->name === '@extends';
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, ExtendsTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Extends_(
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
}
+41
View File
@@ -0,0 +1,41 @@
<?php
/*
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*
*/
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use InvalidArgumentException;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\Types\Context as TypeContext;
interface Factory
{
/**
* Factory method responsible for instantiating the correct sub type.
*
* @param string $tagLine The text for this tag, including description.
*
* @return Tag A new tag object.
*
* @throws InvalidArgumentException If an invalid tag line was presented.
*/
public function create(string $tagLine, ?TypeContext $context = null): Tag;
}
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Implements_;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\ImplementsTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class ImplementsFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof ImplementsTagValueNode && $node->name === '@implements';
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, ImplementsTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Implements_(
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
}
@@ -0,0 +1,82 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Method;
use phpDocumentor\Reflection\DocBlock\Tags\MethodParameter;
use phpDocumentor\Reflection\Type;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use phpDocumentor\Reflection\Types\Mixed_;
use phpDocumentor\Reflection\Types\Void_;
use PHPStan\PhpDocParser\Ast\PhpDoc\MethodTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\MethodTagValueParameterNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use Webmozart\Assert\Assert;
use function array_map;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class MethodFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, MethodTagValueNode::class);
return new Method(
$tagValue->methodName,
array_map(
function (MethodTagValueParameterNode $param) use ($context) {
return new MethodParameter(
trim($param->parameterName, '$'),
$param->type === null ? new Mixed_() : $this->typeResolver->createType(
$param->type,
$context
),
$param->isReference,
$param->isVariadic,
$param->defaultValue === null ?
MethodParameter::NO_DEFAULT_VALUE :
(string) $param->defaultValue
);
},
$tagValue->parameters
),
$this->createReturnType($tagValue, $context),
$tagValue->isStatic,
$this->descriptionFactory->create($tagValue->description, $context),
false,
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof MethodTagValueNode;
}
private function createReturnType(MethodTagValueNode $tagValue, Context $context): Type
{
if ($tagValue->returnType === null) {
return new Void_();
}
return $this->typeResolver->createType($tagValue->returnType, $context);
}
}
@@ -0,0 +1,100 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use function array_key_last;
use function get_class;
use function gettype;
use function method_exists;
use function ucfirst;
use function var_export;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class MethodParameterFactory
{
/**
* Formats the given default value to a string-able mixin
*
* @param mixed $defaultValue
*/
public function format($defaultValue): string
{
$method = 'format' . ucfirst(gettype($defaultValue));
if (method_exists($this, $method)) {
return $this->{$method}($defaultValue);
}
return '';
}
private function formatDouble(float $defaultValue): string
{
return var_export($defaultValue, true);
}
/**
* @param mixed $defaultValue
*/
private function formatNull($defaultValue): string
{
return 'null';
}
private function formatInteger(int $defaultValue): string
{
return var_export($defaultValue, true);
}
private function formatString(string $defaultValue): string
{
return var_export($defaultValue, true);
}
private function formatBoolean(bool $defaultValue): string
{
return var_export($defaultValue, true);
}
/**
* @param array<(array<mixed>|int|float|bool|string|object|null)> $defaultValue
*/
private function formatArray(array $defaultValue): string
{
$formatedValue = '[';
foreach ($defaultValue as $key => $value) {
$method = 'format' . ucfirst(gettype($value));
if (!method_exists($this, $method)) {
continue;
}
$formatedValue .= $this->{$method}($value);
if ($key === array_key_last($defaultValue)) {
continue;
}
$formatedValue .= ',';
}
return $formatedValue . ']';
}
private function formatObject(object $defaultValue): string
{
return 'new ' . get_class($defaultValue) . '()';
}
}
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Mixin;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\MixinTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class MixinFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, MixinTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Mixin(
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof MixinTagValueNode;
}
}
@@ -0,0 +1,16 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
interface PHPStanFactory
{
public function create(PhpDocTagNode $node, Context $context): Tag;
public function supports(PhpDocTagNode $node, Context $context): bool;
}
@@ -0,0 +1,84 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\InvalidTag;
use phpDocumentor\Reflection\DocBlock\Tags\Param;
use phpDocumentor\Reflection\Exception\ParserException;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\InvalidTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\ParamTagValueNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\TypelessParamTagValueNode;
use PHPStan\PhpDocParser\Ast\Type\IdentifierTypeNode;
use PHPStan\PhpDocParser\Ast\Type\OffsetAccessTypeNode;
use Webmozart\Assert\Assert;
use function is_string;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class ParamFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
if ($tagValue instanceof InvalidTagValueNode) {
return InvalidTag::create($tagValue->value, 'param')->withError(
ParserException::from($tagValue->exception)
);
}
Assert::isInstanceOfAny(
$tagValue,
[
ParamTagValueNode::class,
TypelessParamTagValueNode::class,
]
);
if (($tagValue->type ?? null) instanceof OffsetAccessTypeNode) {
return InvalidTag::create(
(string) $tagValue,
'param'
);
}
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Param(
trim($tagValue->parameterName, '$'),
$this->typeResolver->createType($tagValue->type ?? new IdentifierTypeNode('mixed'), $context),
$tagValue->isVariadic,
$this->descriptionFactory->create($description, $context),
$tagValue->isReference
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof ParamTagValueNode
|| $node->value instanceof TypelessParamTagValueNode
|| $node->name === '@param';
}
}
@@ -0,0 +1,54 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Property;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PropertyTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class PropertyFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, PropertyTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Property(
trim($tagValue->propertyName, '$'),
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof PropertyTagValueNode && $node->name === '@property';
}
}
@@ -0,0 +1,54 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\PropertyRead;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PropertyTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class PropertyReadFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->typeResolver = $typeResolver;
$this->descriptionFactory = $descriptionFactory;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, PropertyTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new PropertyRead(
trim($tagValue->propertyName, '$'),
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof PropertyTagValueNode && $node->name === '@property-read';
}
}
@@ -0,0 +1,54 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\PropertyWrite;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\PropertyTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class PropertyWriteFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, PropertyTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new PropertyWrite(
trim($tagValue->propertyName, '$'),
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof PropertyTagValueNode && $node->name === '@property-write';
}
}
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Return_;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\ReturnTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class ReturnFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, ReturnTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Return_(
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof ReturnTagValueNode;
}
}
@@ -0,0 +1,53 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\TemplateCovariant;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\TemplateTagValueNode;
use PHPStan\PhpDocParser\Ast\Type\IdentifierTypeNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class TemplateCovariantFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof TemplateTagValueNode && $node->name === '@template-covariant';
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, TemplateTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new TemplateCovariant(
$this->typeResolver->createType(new IdentifierTypeNode($tagValue->name), $context),
$this->descriptionFactory->create($description, $context)
);
}
}
@@ -0,0 +1,56 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Template;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\TemplateTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class TemplateFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, TemplateTagValueNode::class);
$name = $tagValue->name;
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Template(
$name,
$this->typeResolver->createType($tagValue->bound, $context),
$this->typeResolver->createType($tagValue->default, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof TemplateTagValueNode && $node->name === '@template';
}
}
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Throws;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\ThrowsTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class ThrowsFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, ThrowsTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Throws(
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof ThrowsTagValueNode;
}
}
+54
View File
@@ -0,0 +1,54 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags\Factory;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Var_;
use phpDocumentor\Reflection\TypeResolver;
use phpDocumentor\Reflection\Types\Context;
use PHPStan\PhpDocParser\Ast\PhpDoc\PhpDocTagNode;
use PHPStan\PhpDocParser\Ast\PhpDoc\VarTagValueNode;
use Webmozart\Assert\Assert;
use function is_string;
use function trim;
/**
* @internal This class is not part of the BC promise of this library.
*/
final class VarFactory implements PHPStanFactory
{
private DescriptionFactory $descriptionFactory;
private TypeResolver $typeResolver;
public function __construct(TypeResolver $typeResolver, DescriptionFactory $descriptionFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->typeResolver = $typeResolver;
}
public function create(PhpDocTagNode $node, Context $context): Tag
{
$tagValue = $node->value;
Assert::isInstanceOf($tagValue, VarTagValueNode::class);
$description = $tagValue->getAttribute('description');
if (is_string($description) === false) {
$description = $tagValue->description;
}
return new Var_(
trim($tagValue->variableName, '$'),
$this->typeResolver->createType($tagValue->type, $context),
$this->descriptionFactory->create($description, $context)
);
}
public function supports(PhpDocTagNode $node, Context $context): bool
{
return $node->value instanceof VarTagValueNode;
}
}
+24
View File
@@ -0,0 +1,24 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Tag;
interface Formatter
{
/**
* Formats a tag into a string representation according to a specific format, such as Markdown.
*/
public function format(Tag $tag): string;
}
@@ -0,0 +1,50 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use function max;
use function str_repeat;
use function strlen;
class AlignFormatter implements Formatter
{
/** @var int The maximum tag name length. */
protected int $maxLen = 0;
/**
* @param Tag[] $tags All tags that should later be aligned with the formatter.
*/
public function __construct(array $tags)
{
foreach ($tags as $tag) {
$this->maxLen = max($this->maxLen, strlen($tag->getName()));
}
}
/**
* Formats the given tag to return a simple plain text version.
*/
public function format(Tag $tag): string
{
return '@' . $tag->getName() .
str_repeat(
' ',
$this->maxLen - strlen($tag->getName()) + 1
) .
$tag;
}
}
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\Tags\Formatter;
use function trim;
class PassthroughFormatter implements Formatter
{
/**
* Formats the given tag to return a simple plain text version.
*/
public function format(Tag $tag): string
{
return trim('@' . $tag->getName() . ' ' . $tag);
}
}
+89
View File
@@ -0,0 +1,89 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use InvalidArgumentException;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\StandardTagFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use Webmozart\Assert\Assert;
use function preg_match;
/**
* Parses a tag definition for a DocBlock.
*/
final class Generic extends BaseTag
{
/**
* Parses a tag and populates the member variables.
*
* @param string $name Name of the tag.
* @param Description $description The contents of the given tag.
*/
public function __construct(string $name, ?Description $description = null)
{
$this->validateTagName($name);
$this->name = $name;
$this->description = $description;
}
/**
* Creates a new tag that represents any unknown tag type.
*
* @return static
*/
public static function create(
string $body,
string $name = '',
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
Assert::stringNotEmpty($name);
Assert::notNull($descriptionFactory);
$description = $body !== '' ? $descriptionFactory->create($body, $context) : null;
return new static($name, $description);
}
/**
* Returns the tag as a serialized string
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
return $description;
}
/**
* Validates if the tag name matches the expected format, otherwise throws an exception.
*/
private function validateTagName(string $name): void
{
if (!preg_match('/^' . StandardTagFactory::REGEX_TAGNAME . '$/u', $name)) {
throw new InvalidArgumentException(
'The tag name "' . $name . '" is not wellformed. Tags may only consist of letters, underscores, '
. 'hyphens and backslashes.'
);
}
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}implements tag in a Docblock.
*/
class Implements_ extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'implements';
$this->type = $type;
$this->description = $description;
}
}
+150
View File
@@ -0,0 +1,150 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags;
use Closure;
use Exception;
use phpDocumentor\Reflection\DocBlock\Tag;
use ReflectionClass;
use ReflectionException;
use ReflectionFunction;
use Throwable;
use function array_map;
use function get_class;
use function get_resource_type;
use function is_array;
use function is_object;
use function is_resource;
use function sprintf;
use const PHP_VERSION_ID;
/**
* This class represents an exception during the tag creation
*
* Since the internals of the library are relaying on the correct syntax of a docblock
* we cannot simply throw exceptions at all time because the exceptions will break the creation of a
* docklock. Just silently ignore the exceptions is not an option because the user as an issue to fix.
*
* This tag holds that error information until a using application is able to display it. The object will just behave
* like any normal tag. So the normal application flow will not break.
*/
final class InvalidTag implements Tag
{
private string $name;
private string $body;
private ?Throwable $throwable = null;
private function __construct(string $name, string $body)
{
$this->name = $name;
$this->body = $body;
}
public function getException(): ?Throwable
{
return $this->throwable;
}
public function getName(): string
{
return $this->name;
}
public static function create(string $body, string $name = ''): self
{
return new self($name, $body);
}
public function withError(Throwable $exception): self
{
$this->flattenExceptionBacktrace($exception);
$tag = new self($this->name, $this->body);
$tag->throwable = $exception;
return $tag;
}
/**
* Removes all complex types from backtrace
*
* Not all objects are serializable. So we need to remove them from the
* stored exception to be sure that we do not break existing library usage.
*/
private function flattenExceptionBacktrace(Throwable $exception): void
{
$traceProperty = (new ReflectionClass(Exception::class))->getProperty('trace');
if (PHP_VERSION_ID < 80100) {
$traceProperty->setAccessible(true);
}
do {
$trace = $exception->getTrace();
if (isset($trace[0]['args'])) {
$trace = array_map(
function (array $call): array {
$call['args'] = array_map([$this, 'flattenArguments'], $call['args'] ?? []);
return $call;
},
$trace
);
}
$traceProperty->setValue($exception, $trace);
$exception = $exception->getPrevious();
} while ($exception !== null);
if (PHP_VERSION_ID >= 80100) {
return;
}
$traceProperty->setAccessible(false);
}
/**
* @param mixed $value
*
* @return mixed
*
* @throws ReflectionException
*/
private function flattenArguments($value)
{
if ($value instanceof Closure) {
$closureReflection = new ReflectionFunction($value);
$value = sprintf(
'(Closure at %s:%s)',
$closureReflection->getFileName(),
$closureReflection->getStartLine()
);
} elseif (is_object($value)) {
$value = sprintf('object(%s)', get_class($value));
} elseif (is_resource($value)) {
$value = sprintf('resource(%s)', get_resource_type($value));
} elseif (is_array($value)) {
$value = array_map([$this, 'flattenArguments'], $value);
}
return $value;
}
public function render(?Formatter $formatter = null): string
{
if ($formatter === null) {
$formatter = new Formatter\PassthroughFormatter();
}
return $formatter->format($this);
}
public function __toString(): string
{
return $this->body;
}
}
+76
View File
@@ -0,0 +1,76 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use phpDocumentor\Reflection\Utils;
use Webmozart\Assert\Assert;
/**
* Reflection class for a {@}link tag in a Docblock.
*/
final class Link extends BaseTag
{
protected string $name = 'link';
private string $link;
/**
* Initializes a link to a URL.
*/
public function __construct(string $link, ?Description $description = null)
{
$this->link = $link;
$this->description = $description;
}
public static function create(
string $body,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
Assert::notNull($descriptionFactory);
$parts = Utils::pregSplit('/\s+/Su', $body, 2);
$description = isset($parts[1]) ? $descriptionFactory->create($parts[1], $context) : null;
return new static($parts[0], $description);
}
/**
* Gets the link
*/
public function getLink(): string
{
return $this->link;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$link = $this->link;
return $link . ($description !== '' ? ($link !== '' ? ' ' : '') . $description : '');
}
}
+135
View File
@@ -0,0 +1,135 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Exception\CannotCreateTag;
use phpDocumentor\Reflection\Type;
use phpDocumentor\Reflection\Types\Void_;
use Webmozart\Assert\Assert;
use function implode;
/**
* Reflection class for an {@}method in a Docblock.
*/
final class Method extends BaseTag
{
protected string $name = 'method';
private string $methodName;
private bool $isStatic;
private Type $returnType;
private bool $returnsReference;
/** @var MethodParameter[] */
private array $parameters;
/**
* @param MethodParameter[] $parameters
*/
public function __construct(
string $methodName,
array $parameters = [],
?Type $returnType = null,
bool $static = false,
?Description $description = null,
bool $returnsReference = false
) {
Assert::stringNotEmpty($methodName);
if ($returnType === null) {
$returnType = new Void_();
}
$this->methodName = $methodName;
$this->returnType = $returnType;
$this->isStatic = $static;
$this->description = $description;
$this->returnsReference = $returnsReference;
$this->parameters = $parameters;
}
/**
* Retrieves the method name.
*/
public function getMethodName(): string
{
return $this->methodName;
}
/** @return MethodParameter[] */
public function getParameters(): array
{
return $this->parameters;
}
/**
* Checks whether the method tag describes a static method or not.
*
* @return bool TRUE if the method declaration is for a static method, FALSE otherwise.
*/
public function isStatic(): bool
{
return $this->isStatic;
}
public function getReturnType(): Type
{
return $this->returnType;
}
public function returnsReference(): bool
{
return $this->returnsReference;
}
public function __toString(): string
{
$arguments = [];
foreach ($this->parameters as $parameter) {
$arguments[] = (string) $parameter;
}
$argumentStr = '(' . implode(', ', $arguments) . ')';
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$static = $this->isStatic ? 'static' : '';
$returnType = (string) $this->returnType;
$methodName = $this->methodName;
$reference = $this->returnsReference ? '&' : '';
return $static
. ($returnType !== '' ? ($static !== '' ? ' ' : '') . $returnType : '')
. ($methodName !== '' ? ($static !== '' || $returnType !== '' ? ' ' : '') . $reference . $methodName : '')
. $argumentStr
. ($description !== '' ? ' ' . $description : '');
}
public static function create(string $body): void
{
throw new CannotCreateTag('Method tag cannot be created');
}
}
+91
View File
@@ -0,0 +1,91 @@
<?php
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
declare(strict_types=1);
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\MethodParameterFactory;
use phpDocumentor\Reflection\Type;
final class MethodParameter
{
private Type $type;
private bool $isReference;
private bool $isVariadic;
private string $name;
/** @var mixed */
private $defaultValue;
public const NO_DEFAULT_VALUE = '__NO_VALUE__';
/**
* @param mixed $defaultValue
*/
public function __construct(
string $name,
Type $type,
bool $isReference = false,
bool $isVariadic = false,
$defaultValue = self::NO_DEFAULT_VALUE
) {
$this->type = $type;
$this->isReference = $isReference;
$this->isVariadic = $isVariadic;
$this->name = $name;
$this->defaultValue = $defaultValue;
}
public function getName(): string
{
return $this->name;
}
public function getType(): Type
{
return $this->type;
}
public function isReference(): bool
{
return $this->isReference;
}
public function isVariadic(): bool
{
return $this->isVariadic;
}
public function getDefaultValue(): ?string
{
if ($this->defaultValue === self::NO_DEFAULT_VALUE) {
return null;
}
return (new MethodParameterFactory())->format($this->defaultValue);
}
public function __toString(): string
{
return $this->getType() . ' ' .
($this->isReference() ? '&' : '') .
($this->isVariadic() ? '...' : '') .
'$' . $this->getName() .
(
$this->defaultValue !== self::NO_DEFAULT_VALUE ?
' = ' . (new MethodParameterFactory())->format($this->defaultValue) :
''
);
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}mixin tag in a Docblock.
*/
final class Mixin extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'mixin';
$this->type = $type;
$this->description = $description;
}
}
+94
View File
@@ -0,0 +1,94 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for the {@}param tag in a Docblock.
*/
final class Param extends TagWithType
{
private ?string $variableName = null;
/** @var bool determines whether this is a variadic argument */
private bool $isVariadic;
/** @var bool determines whether this is passed by reference */
private bool $isReference;
public function __construct(
?string $variableName,
?Type $type = null,
bool $isVariadic = false,
?Description $description = null,
bool $isReference = false
) {
$this->name = 'param';
$this->variableName = $variableName;
$this->type = $type;
$this->isVariadic = $isVariadic;
$this->description = $description;
$this->isReference = $isReference;
}
/**
* Returns the variable's name.
*/
public function getVariableName(): ?string
{
return $this->variableName;
}
/**
* Returns whether this tag is variadic.
*/
public function isVariadic(): bool
{
return $this->isVariadic;
}
/**
* Returns whether this tag is passed by reference.
*/
public function isReference(): bool
{
return $this->isReference;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$variableName = '';
if ($this->variableName !== null && $this->variableName !== '') {
$variableName .= ($this->isReference ? '&' : '') . ($this->isVariadic ? '...' : '');
$variableName .= '$' . $this->variableName;
}
$type = (string) $this->type;
return $type
. ($variableName !== '' ? ($type !== '' ? ' ' : '') . $variableName : '')
. ($description !== '' ? ($type !== '' || $variableName !== '' ? ' ' : '') . $description : '');
}
}
+68
View File
@@ -0,0 +1,68 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
use Webmozart\Assert\Assert;
/**
* Reflection class for a {@}property tag in a Docblock.
*/
final class Property extends TagWithType
{
protected ?string $variableName = null;
public function __construct(?string $variableName, ?Type $type = null, ?Description $description = null)
{
Assert::string($variableName);
$this->name = 'property';
$this->variableName = $variableName;
$this->type = $type;
$this->description = $description;
}
/**
* Returns the variable's name.
*/
public function getVariableName(): ?string
{
return $this->variableName;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description !== null) {
$description = $this->description->render();
} else {
$description = '';
}
if ($this->variableName !== null && $this->variableName !== '') {
$variableName = '$' . $this->variableName;
} else {
$variableName = '';
}
$type = (string) $this->type;
return $type
. ($variableName !== '' ? ($type !== '' ? ' ' : '') . $variableName : '')
. ($description !== '' ? ($type !== '' || $variableName !== '' ? ' ' : '') . $description : '');
}
}
+68
View File
@@ -0,0 +1,68 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
use Webmozart\Assert\Assert;
/**
* Reflection class for a {@}property-read tag in a Docblock.
*/
final class PropertyRead extends TagWithType
{
protected ?string $variableName = null;
public function __construct(?string $variableName, ?Type $type = null, ?Description $description = null)
{
Assert::string($variableName);
$this->name = 'property-read';
$this->variableName = $variableName;
$this->type = $type;
$this->description = $description;
}
/**
* Returns the variable's name.
*/
public function getVariableName(): ?string
{
return $this->variableName;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description !== null) {
$description = $this->description->render();
} else {
$description = '';
}
if ($this->variableName !== null && $this->variableName !== '') {
$variableName = '$' . $this->variableName;
} else {
$variableName = '';
}
$type = (string) $this->type;
return $type
. ($variableName !== '' ? ($type !== '' ? ' ' : '') . $variableName : '')
. ($description !== '' ? ($type !== '' || $variableName !== '' ? ' ' : '') . $description : '');
}
}
+68
View File
@@ -0,0 +1,68 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
use Webmozart\Assert\Assert;
/**
* Reflection class for a {@}property-write tag in a Docblock.
*/
final class PropertyWrite extends TagWithType
{
protected string $variableName;
public function __construct(?string $variableName, ?Type $type = null, ?Description $description = null)
{
Assert::string($variableName);
$this->name = 'property-write';
$this->variableName = $variableName;
$this->type = $type;
$this->description = $description;
}
/**
* Returns the variable's name.
*/
public function getVariableName(): ?string
{
return $this->variableName;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
if ($this->variableName) {
$variableName = '$' . $this->variableName;
} else {
$variableName = '';
}
$type = (string) $this->type;
return $type
. ($variableName !== '' ? ($type !== '' ? ' ' : '') . $variableName : '')
. ($description !== '' ? ($type !== '' || $variableName !== '' ? ' ' : '') . $description : '');
}
}
+37
View File
@@ -0,0 +1,37 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Reference;
use phpDocumentor\Reflection\Fqsen as RealFqsen;
/**
* Fqsen reference used by {@see \phpDocumentor\Reflection\DocBlock\Tags\See}
*/
final class Fqsen implements Reference
{
private RealFqsen $fqsen;
public function __construct(RealFqsen $fqsen)
{
$this->fqsen = $fqsen;
}
/**
* @return string string representation of the referenced fqsen
*/
public function __toString(): string
{
return (string) $this->fqsen;
}
}
+22
View File
@@ -0,0 +1,22 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Reference;
/**
* Interface for references in {@see \phpDocumentor\Reflection\DocBlock\Tags\See}
*/
interface Reference
{
public function __toString(): string;
}
+35
View File
@@ -0,0 +1,35 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags\Reference;
use Webmozart\Assert\Assert;
/**
* Url reference used by {@see \phpDocumentor\Reflection\DocBlock\Tags\See}
*/
final class Url implements Reference
{
private string $uri;
public function __construct(string $uri)
{
Assert::stringNotEmpty($uri);
$this->uri = $uri;
}
public function __toString(): string
{
return $this->uri;
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}return tag in a Docblock.
*/
final class Return_ extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'return';
$this->type = $type;
$this->description = $description;
}
}
+104
View File
@@ -0,0 +1,104 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Reference\Fqsen as FqsenRef;
use phpDocumentor\Reflection\DocBlock\Tags\Reference\Reference;
use phpDocumentor\Reflection\DocBlock\Tags\Reference\Url;
use phpDocumentor\Reflection\Fqsen;
use phpDocumentor\Reflection\FqsenResolver;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use phpDocumentor\Reflection\Utils;
use Webmozart\Assert\Assert;
use function array_key_exists;
use function explode;
use function preg_match;
/**
* Reflection class for an {@}see tag in a Docblock.
*/
final class See extends BaseTag
{
protected string $name = 'see';
protected Reference $refers;
/**
* Initializes this tag.
*/
public function __construct(Reference $refers, ?Description $description = null)
{
$this->refers = $refers;
$this->description = $description;
}
public static function create(
string $body,
?FqsenResolver $typeResolver = null,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
Assert::notNull($descriptionFactory);
$parts = Utils::pregSplit('/\s+/Su', $body, 2);
$description = isset($parts[1]) ? $descriptionFactory->create($parts[1], $context) : null;
// https://tools.ietf.org/html/rfc2396#section-3
if (preg_match('#\w://\w#', $parts[0])) {
return new static(new Url($parts[0]), $description);
}
return new static(new FqsenRef(self::resolveFqsen($parts[0], $typeResolver, $context)), $description);
}
private static function resolveFqsen(string $parts, ?FqsenResolver $fqsenResolver, ?TypeContext $context): Fqsen
{
Assert::notNull($fqsenResolver);
$fqsenParts = explode('::', $parts);
$resolved = $fqsenResolver->resolve($fqsenParts[0], $context);
if (!array_key_exists(1, $fqsenParts)) {
return $resolved;
}
return new Fqsen($resolved . '::' . $fqsenParts[1]);
}
/**
* Returns the ref of this tag.
*/
public function getReference(): Reference
{
return $this->refers;
}
/**
* Returns a string representation of this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$refers = (string) $this->refers;
return $refers . ($description !== '' ? ($refers !== '' ? ' ' : '') . $description : '');
}
}
+102
View File
@@ -0,0 +1,102 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use Webmozart\Assert\Assert;
use function preg_match;
/**
* Reflection class for a {@}since tag in a Docblock.
*/
final class Since extends BaseTag
{
protected string $name = 'since';
/**
* PCRE regular expression matching a version vector.
* Assumes the "x" modifier.
*/
public const REGEX_VECTOR = '(?:
# Normal release vectors.
\d\S*
|
# VCS version vectors. Per PHPCS, they are expected to
# follow the form of the VCS name, followed by ":", followed
# by the version vector itself.
# By convention, popular VCSes like CVS, SVN and GIT use "$"
# around the actual version vector.
[^\s\:]+\:\s*\$[^\$]+\$
)';
/** @var string|null The version vector. */
private ?string $version = null;
public function __construct(?string $version = null, ?Description $description = null)
{
Assert::nullOrNotEmpty($version);
$this->version = $version;
$this->description = $description;
}
public static function create(
?string $body,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): ?self {
if ($body === null || $body === '') {
return new static();
}
$matches = [];
if (!preg_match('/^(' . self::REGEX_VECTOR . ')\s*(.+)?$/sux', $body, $matches)) {
return null;
}
Assert::notNull($descriptionFactory);
return new static(
$matches[1],
$descriptionFactory->create($matches[2] ?? '', $context)
);
}
/**
* Gets the version section of the tag.
*/
public function getVersion(): ?string
{
return $this->version;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description !== null) {
$description = $this->description->render();
} else {
$description = '';
}
$version = (string) $this->version;
return $version . ($description !== '' ? ($version !== '' ? ' ' : '') . $description : '');
}
}
+115
View File
@@ -0,0 +1,115 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use Webmozart\Assert\Assert;
use function preg_match;
/**
* Reflection class for a {@}source tag in a Docblock.
*/
final class Source extends BaseTag
{
protected string $name = 'source';
/** @var int The starting line, relative to the structural element's location. */
private int $startingLine;
/** @var int|null The number of lines, relative to the starting line. NULL means "to the end". */
private ?int $lineCount = null;
/**
* @param int|string $startingLine should be a to int convertible value
* @param int|string|null $lineCount should be a to int convertible value
*/
public function __construct($startingLine, $lineCount = null, ?Description $description = null)
{
Assert::integerish($startingLine);
Assert::nullOrIntegerish($lineCount);
$this->startingLine = (int) $startingLine;
$this->lineCount = $lineCount !== null ? (int) $lineCount : null;
$this->description = $description;
}
public static function create(
string $body,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
Assert::stringNotEmpty($body);
Assert::notNull($descriptionFactory);
$startingLine = 1;
$lineCount = null;
$description = null;
// Starting line / Number of lines / Description
if (preg_match('/^([1-9]\d*)\s*(?:((?1))\s+)?(.*)$/sux', $body, $matches)) {
$startingLine = (int) $matches[1];
if (isset($matches[2]) && $matches[2] !== '') {
$lineCount = (int) $matches[2];
}
$description = $matches[3];
}
return new static($startingLine, $lineCount, $descriptionFactory->create($description ?? '', $context));
}
/**
* Gets the starting line.
*
* @return int The starting line, relative to the structural element's
* location.
*/
public function getStartingLine(): int
{
return $this->startingLine;
}
/**
* Returns the number of lines.
*
* @return int|null The number of lines, relative to the starting line. NULL
* means "to the end".
*/
public function getLineCount(): ?int
{
return $this->lineCount;
}
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$startingLine = (string) $this->startingLine;
$lineCount = $this->lineCount !== null ? ' ' . $this->lineCount : '';
return $startingLine
. $lineCount
. ($description !== ''
? ' ' . $description
: '');
}
}
+50
View File
@@ -0,0 +1,50 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\Exception\CannotCreateTag;
use phpDocumentor\Reflection\Type;
abstract class TagWithType extends BaseTag
{
/** @var ?Type */
protected ?Type $type = null;
/**
* Returns the type section of the variable.
*/
public function getType(): ?Type
{
return $this->type;
}
final public static function create(string $body): Tag
{
throw new CannotCreateTag('Typed tag cannot be created');
}
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$type = (string) $this->type;
return $type . ($description !== '' ? ($type !== '' ? ' ' : '') . $description : '');
}
}
+85
View File
@@ -0,0 +1,85 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\Exception\CannotCreateTag;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}template tag in a Docblock.
*/
final class Template extends BaseTag
{
/** @var non-empty-string */
private string $templateName;
/** @var ?Type The real type */
private ?Type $bound;
private ?Type $default;
/** @param non-empty-string $templateName */
public function __construct(
string $templateName,
?Type $bound = null,
?Type $default = null,
?Description $description = null
) {
$this->name = 'template';
$this->templateName = $templateName;
$this->bound = $bound;
$this->default = $default;
$this->description = $description;
}
/**
* @deprecated Create using static factory is deprecated,
* this method should not be called directly by library consumers
*/
public static function create(string $body): ?Tag
{
throw new CannotCreateTag('Template tag cannot be created');
}
public function getTemplateName(): string
{
return $this->templateName;
}
public function getBound(): ?Type
{
return $this->bound;
}
public function getDefault(): ?Type
{
return $this->default;
}
public function __toString(): string
{
$bound = $this->bound !== null ? ' of ' . $this->bound : '';
$default = $this->default !== null ? ' = ' . $this->default : '';
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
return $this->templateName . $bound . $default . ($description !== '' ? ' ' . $description : '');
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}template-covariant tag in a Docblock.
*/
final class TemplateCovariant extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'template-covariant';
$this->type = $type;
$this->description = $description;
}
}
+29
View File
@@ -0,0 +1,29 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}template-extends tag in a Docblock.
*/
final class TemplateExtends extends Extends_
{
public function __construct(Type $type, ?Description $description = null)
{
parent::__construct($type, $description);
$this->name = 'template-extends';
}
}
+29
View File
@@ -0,0 +1,29 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}template-implements tag in a Docblock.
*/
final class TemplateImplements extends Implements_
{
public function __construct(Type $type, ?Description $description = null)
{
parent::__construct($type, $description);
$this->name = 'template-implements';
}
}
+30
View File
@@ -0,0 +1,30 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
/**
* Reflection class for a {@}throws tag in a Docblock.
*/
final class Throws extends TagWithType
{
public function __construct(Type $type, ?Description $description = null)
{
$this->name = 'throws';
$this->type = $type;
$this->description = $description;
}
}
+98
View File
@@ -0,0 +1,98 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Fqsen;
use phpDocumentor\Reflection\FqsenResolver;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use phpDocumentor\Reflection\Utils;
use Webmozart\Assert\Assert;
use function array_key_exists;
use function explode;
/**
* Reflection class for a {@}uses tag in a Docblock.
*/
final class Uses extends BaseTag
{
protected string $name = 'uses';
protected Fqsen $refers;
/**
* Initializes this tag.
*/
public function __construct(Fqsen $refers, ?Description $description = null)
{
$this->refers = $refers;
$this->description = $description;
}
public static function create(
string $body,
?FqsenResolver $resolver = null,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): self {
Assert::notNull($resolver);
Assert::notNull($descriptionFactory);
$parts = Utils::pregSplit('/\s+/Su', $body, 2);
return new static(
self::resolveFqsen($parts[0], $resolver, $context),
$descriptionFactory->create($parts[1] ?? '', $context)
);
}
private static function resolveFqsen(string $parts, ?FqsenResolver $fqsenResolver, ?TypeContext $context): Fqsen
{
Assert::notNull($fqsenResolver);
$fqsenParts = explode('::', $parts);
$resolved = $fqsenResolver->resolve($fqsenParts[0], $context);
if (!array_key_exists(1, $fqsenParts)) {
return $resolved;
}
return new Fqsen($resolved . '::' . $fqsenParts[1]);
}
/**
* Returns the structural element this tag refers to.
*/
public function getReference(): Fqsen
{
return $this->refers;
}
/**
* Returns a string representation of this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$refers = (string) $this->refers;
return $refers . ($description !== '' ? ($refers !== '' ? ' ' : '') . $description : '');
}
}
+68
View File
@@ -0,0 +1,68 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\Type;
use Webmozart\Assert\Assert;
/**
* Reflection class for a {@}var tag in a Docblock.
*/
final class Var_ extends TagWithType
{
protected ?string $variableName = '';
public function __construct(?string $variableName, ?Type $type = null, ?Description $description = null)
{
Assert::string($variableName);
$this->name = 'var';
$this->variableName = $variableName;
$this->type = $type;
$this->description = $description;
}
/**
* Returns the variable's name.
*/
public function getVariableName(): ?string
{
return $this->variableName;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description !== null) {
$description = $this->description->render();
} else {
$description = '';
}
if ($this->variableName !== null && $this->variableName !== '') {
$variableName = '$' . $this->variableName;
} else {
$variableName = '';
}
$type = (string) $this->type;
return $type
. ($variableName !== '' ? ($type !== '' ? ' ' : '') . $variableName : '')
. ($description !== '' ? ($type !== '' || $variableName !== '' ? ' ' : '') . $description : '');
}
}
+105
View File
@@ -0,0 +1,105 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection\DocBlock\Tags;
use phpDocumentor\Reflection\DocBlock\Description;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\Types\Context as TypeContext;
use Webmozart\Assert\Assert;
use function preg_match;
/**
* Reflection class for a {@}version tag in a Docblock.
*/
final class Version extends BaseTag
{
protected string $name = 'version';
/**
* PCRE regular expression matching a version vector.
* Assumes the "x" modifier.
*/
public const REGEX_VECTOR = '(?:
# Normal release vectors.
\d\S*
|
# VCS version vectors. Per PHPCS, they are expected to
# follow the form of the VCS name, followed by ":", followed
# by the version vector itself.
# By convention, popular VCSes like CVS, SVN and GIT use "$"
# around the actual version vector.
[^\s\:]+\:\s*\$[^\$]+\$
)';
/** @var string|null The version vector. */
private ?string $version = null;
public function __construct(?string $version = null, ?Description $description = null)
{
Assert::nullOrStringNotEmpty($version);
$this->version = $version;
$this->description = $description;
}
public static function create(
?string $body,
?DescriptionFactory $descriptionFactory = null,
?TypeContext $context = null
): ?self {
if ($body === null || $body === '') {
return new static();
}
$matches = [];
if (!preg_match('/^(' . self::REGEX_VECTOR . ')\s*(.+)?$/sux', $body, $matches)) {
return null;
}
$description = null;
if ($descriptionFactory !== null) {
$description = $descriptionFactory->create($matches[2] ?? '', $context);
}
return new static(
$matches[1],
$description
);
}
/**
* Gets the version section of the tag.
*/
public function getVersion(): ?string
{
return $this->version;
}
/**
* Returns a string representation for this tag.
*/
public function __toString(): string
{
if ($this->description) {
$description = $this->description->render();
} else {
$description = '';
}
$version = (string) $this->version;
return $version . ($description !== '' ? ($version !== '' ? ' ' : '') . $description : '');
}
}
+284
View File
@@ -0,0 +1,284 @@
<?php
declare(strict_types=1);
/**
* This file is part of phpDocumentor.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*
* @link http://phpdoc.org
*/
namespace phpDocumentor\Reflection;
use InvalidArgumentException;
use LogicException;
use phpDocumentor\Reflection\DocBlock\DescriptionFactory;
use phpDocumentor\Reflection\DocBlock\StandardTagFactory;
use phpDocumentor\Reflection\DocBlock\Tag;
use phpDocumentor\Reflection\DocBlock\TagFactory;
use phpDocumentor\Reflection\DocBlock\Tags\Factory\Factory;
use Webmozart\Assert\Assert;
use function array_shift;
use function count;
use function explode;
use function is_object;
use function method_exists;
use function preg_match;
use function preg_replace;
use function str_replace;
use function strpos;
use function substr;
use function trim;
final class DocBlockFactory implements DocBlockFactoryInterface
{
private DocBlock\DescriptionFactory $descriptionFactory;
private TagFactory $tagFactory;
/**
* Initializes this factory with the required subcontractors.
*/
public function __construct(DescriptionFactory $descriptionFactory, TagFactory $tagFactory)
{
$this->descriptionFactory = $descriptionFactory;
$this->tagFactory = $tagFactory;
}
/**
* Factory method for easy instantiation.
*
* @param array<string, class-string<Tag>|Factory> $additionalTags
*/
public static function createInstance(array $additionalTags = []): DocBlockFactoryInterface
{
$fqsenResolver = new FqsenResolver();
$tagFactory = StandardTagFactory::createInstance($fqsenResolver);
$descriptionFactory = new DescriptionFactory($tagFactory);
$docBlockFactory = new self($descriptionFactory, $tagFactory);
foreach ($additionalTags as $tagName => $tagHandler) {
$docBlockFactory->registerTagHandler($tagName, $tagHandler);
}
return $docBlockFactory;
}
/**
* @param object|string $docblock A string containing the DocBlock to parse or an object supporting the
* getDocComment method (such as a ReflectionClass object).
*/
public function create($docblock, ?Types\Context $context = null, ?Location $location = null): DocBlock
{
if (is_object($docblock)) {
if (!method_exists($docblock, 'getDocComment')) {
$exceptionMessage = 'Invalid object passed; the given object must support the getDocComment method';
throw new InvalidArgumentException($exceptionMessage);
}
$docblock = $docblock->getDocComment();
Assert::string($docblock);
}
Assert::stringNotEmpty($docblock);
if ($context === null) {
$context = new Types\Context('');
}
$parts = $this->splitDocBlock($this->stripDocComment($docblock));
[$templateMarker, $summary, $description, $tags] = $parts;
return new DocBlock(
$summary,
$description ? $this->descriptionFactory->create($description, $context) : null,
$this->parseTagBlock($tags, $context),
$context,
$location,
$templateMarker === '#@+',
$templateMarker === '#@-'
);
}
/**
* @param class-string<Tag>|Factory $handler
*/
public function registerTagHandler(string $tagName, $handler): void
{
$this->tagFactory->registerTagHandler($tagName, $handler);
}
/**
* Strips the asterisks from the DocBlock comment.
*
* @param string $comment String containing the comment text.
*/
private function stripDocComment(string $comment): string
{
$comment = preg_replace('#[ \t]*(?:\/\*\*|\*\/|\*)?[ \t]?(.*)?#u', '$1', $comment);
Assert::string($comment);
$comment = trim($comment);
// reg ex above is not able to remove */ from a single line docblock
if (substr($comment, -2) === '*/') {
$comment = trim(substr($comment, 0, -2));
}
return str_replace(["\r\n", "\r"], "\n", $comment);
}
// phpcs:disable
/**
* Splits the DocBlock into a template marker, summary, description and block of tags.
*
* @param string $comment Comment to split into the sub-parts.
*
* @return string[] containing the template marker (if any), summary, description and a string containing the tags.
*
* @author Mike van Riel <[email protected]> for extending the regex with template marker support.
*
* @author Richard van Velzen (@_richardJ) Special thanks to Richard for the regex responsible for the split.
*/
private function splitDocBlock(string $comment): array
{
// phpcs:enable
// Performance improvement cheat: if the first character is an @ then only tags are in this DocBlock. This
// method does not split tags so we return this verbatim as the fourth result (tags). This saves us the
// performance impact of running a regular expression
if (strpos($comment, '@') === 0) {
return ['', '', '', $comment];
}
// clears all extra horizontal whitespace from the line endings to prevent parsing issues
$comment = preg_replace('/\h*$/Sum', '', $comment);
Assert::string($comment);
/*
* Splits the docblock into a template marker, summary, description and tags section.
*
* - The template marker is empty, #@+ or #@- if the DocBlock starts with either of those (a newline may
* occur after it and will be stripped).
* - The short description is started from the first character until a dot is encountered followed by a
* newline OR two consecutive newlines (horizontal whitespace is taken into account to consider spacing
* errors). This is optional.
* - The long description, any character until a new line is encountered followed by an @ and word
* characters (a tag). This is optional.
* - Tags; the remaining characters
*
* Big thanks to RichardJ for contributing this Regular Expression
*/
preg_match(
'/
\A
# 1. Extract the template marker
(?:(\#\@\+|\#\@\-)\n?)?
# 2. Extract the summary
(?:
(?! @\pL ) # The summary may not start with an @
(
[^\n.]+
(?:
(?! \. \n | \n{2} ) # End summary upon a dot followed by newline or two newlines
[\n.]* (?! [ \t]* @\pL ) # End summary when an @ is found as first character on a new line
[^\n.]+ # Include anything else
)*
\.?
)?
)
# 3. Extract the description
(?:
\s* # Some form of whitespace _must_ precede a description because a summary must be there
(?! @\pL ) # The description may not start with an @
(
[^\n]+
(?: \n+
(?! [ \t]* @\pL ) # End description when an @ is found as first character on a new line
[^\n]+ # Include anything else
)*
)
)?
# 4. Extract the tags (anything that follows)
(\s+ [\s\S]*)? # everything that follows
/ux',
$comment,
$matches
);
array_shift($matches);
while (count($matches) < 4) {
$matches[] = '';
}
return $matches;
}
/**
* Creates the tag objects.
*
* @param string $tags Tag block to parse.
* @param Types\Context $context Context of the parsed Tag
*
* @return DocBlock\Tag[]
*/
private function parseTagBlock(string $tags, Types\Context $context): array
{
$tags = $this->filterTagBlock($tags);
if ($tags === null) {
return [];
}
$result = [];
$lines = $this->splitTagBlockIntoTagLines($tags);
foreach ($lines as $key => $tagLine) {
$result[$key] = $this->tagFactory->create(trim($tagLine), $context);
}
return $result;
}
/**
* @return string[]
*/
private function splitTagBlockIntoTagLines(string $tags): array
{
$result = [];
foreach (explode("\n", $tags) as $tagLine) {
if ($tagLine !== '' && strpos($tagLine, '@') === 0) {
$result[] = $tagLine;
} else {
$result[count($result) - 1] .= "\n" . $tagLine;
}
}
return $result;
}
private function filterTagBlock(string $tags): ?string
{
$tags = trim($tags);
if (!$tags) {
return null;
}
if ($tags[0] !== '@') {
// @codeCoverageIgnoreStart
// Can't simulate this; this only happens if there is an error with the parsing of the DocBlock that
// we didn't foresee.
throw new LogicException('A tag block started with text instead of an at-sign(@): ' . $tags);
// @codeCoverageIgnoreEnd
}
return $tags;
}
}
+23
View File
@@ -0,0 +1,23 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection;
use phpDocumentor\Reflection\DocBlock\Tag;
// phpcs:ignore SlevomatCodingStandard.Classes.SuperfluousInterfaceNaming.SuperfluousSuffix
interface DocBlockFactoryInterface
{
/**
* Factory method for easy instantiation.
*
* @param array<string, class-string<Tag>> $additionalTags
*/
public static function createInstance(array $additionalTags = []): self;
/**
* @param string|object $docblock
*/
public function create($docblock, ?Types\Context $context = null, ?Location $location = null): DocBlock;
}
+11
View File
@@ -0,0 +1,11 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\Exception;
use LogicException;
final class CannotCreateTag extends LogicException
{
}
+19
View File
@@ -0,0 +1,19 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\Exception;
use InvalidArgumentException;
final class ParserException extends InvalidArgumentException implements ReflectionDocblockException
{
public static function from(\PHPStan\PhpDocParser\Parser\ParserException $exception): self
{
return new self(
'Failed to parse docblock: ' . $exception->getMessage(),
0,
$exception
);
}
}
+44
View File
@@ -0,0 +1,44 @@
<?php
declare(strict_types=1);
namespace phpDocumentor\Reflection\Exception;
use InvalidArgumentException;
use const PREG_BACKTRACK_LIMIT_ERROR;
use const PREG_BAD_UTF8_ERROR;
use const PREG_BAD_UTF8_OFFSET_ERROR;
use const PREG_INTERNAL_ERROR;
use const PREG_JIT_STACKLIMIT_ERROR;
use const PREG_NO_ERROR;
use const PREG_RECURSION_LIMIT_ERROR;
final class PcreException extends InvalidArgumentException
{
public static function createFromPhpError(int $errorCode): self
{
switch ($errorCode) {
case PREG_BACKTRACK_LIMIT_ERROR:
return new self('Backtrack limit error');
case PREG_RECURSION_LIMIT_ERROR:
return new self('Recursion limit error');
case PREG_BAD_UTF8_ERROR:
return new self('Bad UTF8 error');
case PREG_BAD_UTF8_OFFSET_ERROR:
return new self('Bad UTF8 offset error');
case PREG_JIT_STACKLIMIT_ERROR:
return new self('Jit stacklimit error');
case PREG_NO_ERROR:
case PREG_INTERNAL_ERROR:
default:
}
return new self('Unknown Pcre error');
}
}

Some files were not shown because too many files have changed in this diff Show More