Skip to content

Commit f90d4c5

Browse files
committed
object constants & enum cases - collect & display deprecation
phpdoc - more lenient version parsing pull deprecated description from deprecated attribute and phpdoc fix zest's show method to get correct display value for element
1 parent b134180 commit f90d4c5

20 files changed

Lines changed: 230 additions & 75 deletions

File tree

src/Debug/Abstraction/Object/Constants.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ class Constants extends AbstractInheritable
4242
'declaredLast' => null,
4343
'declaredOrig' => null,
4444
'declaredPrev' => null,
45+
'isDeprecated' => false,
4546
'isFinal' => false,
4647
'phpDoc' => array(
4748
'desc' => '',
@@ -170,6 +171,7 @@ private function getCaseRefInfo(ReflectionEnumUnitCase $refCase)
170171
'attributes' => $this->attributeCollect
171172
? $this->helper->getAttributes($refCase)
172173
: array(),
174+
'isDeprecated' => (PHP_VERSION_ID >= 80400 && $refCase->isDeprecated()) || isset($phpDoc['deprecated']),
173175
'isFinal' => $refCase->isFinal(),
174176
'phpDoc' => $phpDoc,
175177
'value' => $refCase instanceof ReflectionEnumBackedCase
@@ -199,6 +201,7 @@ private function getConstantRefInfo(ReflectionClassConstant $refConstant)
199201
'attributes' => $this->attributeCollect
200202
? $this->helper->getAttributes($refConstant)
201203
: array(),
204+
'isDeprecated' => (PHP_VERSION_ID >= 80400 && $refConstant->isDeprecated()) || isset($phpDoc['deprecated']),
202205
'isFinal' => PHP_VERSION_ID >= 80100 && $refConstant->isFinal(),
203206
'phpDoc' => $phpDoc,
204207
'type' => $type,

src/Debug/Abstraction/Object/Helper.php

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
use bdk\Debug\Abstraction\Abstraction;
1616
use bdk\Debug\Abstraction\AbstractObject;
1717
use bdk\Debug\Abstraction\Object\Abstraction as ObjectAbstraction;
18+
use bdk\Debug\Utility\ArrayUtil;
1819
use bdk\Debug\Utility\Php as PhpUtil;
1920
use bdk\Debug\Utility\PhpDoc;
2021
use ReflectionAttribute;
@@ -85,7 +86,12 @@ public static function getAttributes(Reflector $reflector)
8586
}
8687
return \array_map(static function (ReflectionAttribute $attribute) {
8788
return array(
88-
'arguments' => $attribute->getArguments(),
89+
'arguments' => $attribute->getName() === 'Deprecated'
90+
? self::toNamedArguments(
91+
$attribute->getArguments(),
92+
['message', 'since']
93+
)
94+
: $attribute->getArguments(),
8995
'name' => $attribute->getName(),
9096
);
9197
}, $reflector->getAttributes());
@@ -245,4 +251,26 @@ protected static function getParamTypeOld(ReflectionParameter $reflector)
245251
}
246252
return null;
247253
}
254+
255+
/**
256+
* Convert positional arguments to named arguments
257+
*
258+
* @param array $arguments Arguments from getArguments()
259+
* @param array $names Names of the parameters
260+
*
261+
* @return array
262+
*/
263+
private static function toNamedArguments(array $arguments, array $names)
264+
{
265+
$namedArgs = \array_intersect_key($arguments, \array_flip($names));
266+
$arguments = \array_diff_key($arguments, $namedArgs);
267+
foreach ($names as $name) {
268+
if (\array_key_exists($name, $namedArgs)) {
269+
continue;
270+
}
271+
$namedArgs[$name] = \array_shift($arguments);
272+
}
273+
ArrayUtil::sortWithOrder($namedArgs, $names, 'key');
274+
return $namedArgs;
275+
}
248276
}

src/Debug/Dump/Html/Object/AbstractSection.php

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -290,18 +290,55 @@ protected function getAttribs(array $info, array $cfg)
290290
'data-attributes' => $info['attributes'],
291291
'data-chars' => $this->valDumper->findChars(\json_encode($info['attributes'], JSON_UNESCAPED_UNICODE)),
292292
'data-declared-prev' => $info['declaredPrev'],
293+
'data-deprecated-desc' => !empty($info['isDeprecated']) ? $this->getDeprecatedDesc($info) : '',
293294
'data-inherited-from' => $info['declaredLast'],
294295
);
295296
$filter = \array_filter(array(
296297
'class' => true,
297298
'data-attributes' => $cfg['attributeOutput'] && $info['attributes'],
298299
'data-chars' => $cfg['attributeOutput'],
299300
'data-declared-prev' => empty($info['isInherited']) && !empty($info['declaredPrev']),
301+
'data-deprecated-desc' => !empty($attribs['data-deprecated-desc']),
300302
'data-inherited-from' => !empty($info['isInherited']) || $info['isPrivateAncestor'],
301303
));
302304
return \array_intersect_key($attribs, $filter);
303305
}
304306

307+
/**
308+
* Get deprecated description from a combination of #Deprecated and @deprecated
309+
*
310+
* @param array $info Abstraction info
311+
*
312+
* @return string
313+
*/
314+
protected function getDeprecatedDesc(array $info)
315+
{
316+
$depAttrs = \array_filter($info['attributes'], static function ($attrInfo) {
317+
return $attrInfo['name'] === 'Deprecated';
318+
});
319+
$depAttr = \array_shift($depAttrs) ?: [];
320+
$desc = '';
321+
if (isset($depAttr['arguments']['message'])) {
322+
$desc = $this->helper->dumpPhpDoc($depAttr['arguments']['message'], array(
323+
'sanitize' => true,
324+
));
325+
} elseif (isset($info['phpDoc']['deprecated'])) {
326+
$desc = $this->helper->dumpPhpDoc($info['phpDoc']['deprecated'][0]['desc']);
327+
}
328+
$since = '';
329+
if (isset($depAttr['arguments']['since'])) {
330+
$since = 'since ' . $this->helper->dumpPhpDoc($depAttr['arguments']['since'], array(
331+
'sanitize' => true,
332+
));
333+
} elseif (isset($info['phpDoc']['deprecated'][0]['version'])) {
334+
$since = 'since ' . $info['phpDoc']['deprecated'][0]['version'];
335+
}
336+
if ($desc && $since) {
337+
$since = '<em>(' . $since . ')</em>';
338+
}
339+
return \implode(' ', \array_filter([$desc, $since]));
340+
}
341+
305342
/**
306343
* Get css classes to apply to item
307344
*

src/Debug/Dump/Html/Object/Methods.php

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,6 @@ public function dump(ObjectAbstraction $abs)
5656
$html .= $this->magicMethodInfo($magicMethods);
5757
$html .= $this->dumpItems($abs, 'methods', array());
5858
return \str_replace([
59-
' data-deprecated-desc="null"',
6059
' data-implements="null"',
6160
' data-throws="null"',
6261
' <span class="t_type"></span>',
@@ -269,9 +268,6 @@ protected function dumpStaticVars(array $info)
269268
protected function getAttribs(array $info, array $cfg)
270269
{
271270
return \array_merge(parent::getAttribs($info, $this->opts), array(
272-
'data-deprecated-desc' => isset($info['phpDoc']['deprecated'])
273-
? $this->helper->dumpPhpDoc($info['phpDoc']['deprecated'][0]['desc'])
274-
: null,
275271
'data-implements' => $info['implements'],
276272
'data-throws' => $this->opts['phpDocOutput'] && isset($info['phpDoc']['throws'])
277273
? \array_map(function ($info) {

src/Debug/Dump/Text.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
use bdk\Debug\LogEntry;
1818

1919
/**
20-
* Base output plugin
20+
* Output log entries as text
2121
*/
2222
class Text extends Base
2323
{

src/Debug/Dump/Text/TextObject.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -203,13 +203,15 @@ protected function dumpPropPrefix(array $info)
203203
{
204204
$info = \array_filter(array(
205205
'inherited' => $info['isInherited'],
206+
'isDeprecated' => $info['isDeprecated'],
206207
'isDynamic' => $info['declaredLast'] === null
207208
&& $info['valueFrom'] === 'value'
208209
&& $info['className'] !== 'stdClass',
209210
'overrides' => $info['isInherited'] === false && $info['declaredPrev'],
210211
));
211212
$prefixes = \array_intersect_key(array(
212213
'inherited' => '',
214+
'isDeprecated' => '',
213215
'isDynamic' => '',
214216
'overrides' => '',
215217
), $info);

src/Debug/Dump/TextAnsi.php

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,15 +17,14 @@
1717
use bdk\Debug\LogEntry;
1818

1919
/**
20-
* Base output plugin
20+
* Output log entries as ANSI text
2121
*/
2222
class TextAnsi extends Text
2323
{
2424
const ESCAPE_RESET = "\x00escapeReset\x00";
2525

2626
/** @var array<string,mixed> */
2727
protected $ansiCfg = array(
28-
'ansi' => 'default', // default | true | false (STDOUT & STDERR streams will default to true)
2928
'escapeCodes' => array(
3029
'arrayKey' => "\e[38;5;83m", // yellow
3130
'binary' => "\e[30;48;5;250m", // black foreground / grey background

src/Debug/Dump/TextAnsi/TextAnsiObject.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,7 @@ protected function dumpPropPrefix(array $info)
193193
$escapeCodesMethods = $this->valDumper->getCfg('escapeCodesMethods');
194194
$escapeReset = $this->valDumper->escapeReset;
195195
return \strtr(parent::dumpPropPrefix($info), array(
196+
'' => $escapeCodesMethods['warn'] . '' . $escapeReset,
196197
'' => $escapeCodes['muted'] . '' . $escapeReset,
197198
'' => $escapeCodesMethods['warn'] . '' . $escapeReset,
198199
'' => $escapeCodes['muted'] . '' . $escapeReset,

src/Debug/Route/Stream.php

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ class Stream extends AbstractRoute
2727

2828
/** @var array<string,mixed> */
2929
protected $cfg = array(
30-
'ansi' => 'default', // default | true | false
30+
'ansi' => 'auto', // auto | default | true | false
3131
'channels' => ['*'],
3232
'channelsExclude' => [
3333
'events',
@@ -157,7 +157,7 @@ public function onLog(LogEntry $logEntry)
157157
private function ansiCheck()
158158
{
159159
return $this->cfg['ansi'] === true
160-
|| ($this->cfg['ansi'] === 'default' && self::hasColorSupport($this->fileHandle));
160+
|| (\in_array($this->cfg['ansi'], ['auto', 'default'], true) && self::hasColorSupport($this->fileHandle));
161161
}
162162

163163
/**
@@ -239,6 +239,16 @@ protected function openStream($stream)
239239
if (!$this->fileHandle) {
240240
return;
241241
}
242+
$this->setDumper();
243+
}
244+
245+
/**
246+
* Set the dumper based on 'ansi' config value
247+
*
248+
* @return void
249+
*/
250+
private function setDumper()
251+
{
242252
$this->dumper = $this->ansiCheck()
243253
? $this->debug->getDump('textAnsi')
244254
: $this->debug->getDump('text');
@@ -287,5 +297,8 @@ protected function postSetCfg($cfg = array(), $prev = array())
287297
// changing stream?
288298
$this->openStream($cfg['stream']);
289299
}
300+
if (isset($cfg['ansi'])) {
301+
$this->setDumper();
302+
}
290303
}
291304
}

src/Debug/Utility/PhpDoc/Parsers.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -308,7 +308,7 @@ private function parserVersion()
308308
return array(
309309
'parts' => ['version', 'desc'],
310310
'regex' => '/^'
311-
. '(?P<version>\d+(?:\.\d+){0,2})?'
311+
. '(?:v)?(?P<version>\d+(?:\.\d+){0,2}(-?\w*)?)?'
312312
. '\s*'
313313
. '(?P<desc>.*)'
314314
. '$/s',

0 commit comments

Comments
 (0)