Skip to content

Commit 03240fc

Browse files
committed
Various minor performance improvements.
1 parent 4545f95 commit 03240fc

4 files changed

Lines changed: 569 additions & 348 deletions

File tree

Changelog.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ Versioning guidelines for SemVer can be found at: https://semver.org/
99

1010
- [2025.11.21]: Added PHP 8.5 to workflows.
1111

12+
- [2026.03.17]: Various minor performance improvements.
13+
1214
=== Version/Release 2.0.1 ===
1315
PATCH RELEASE.
1416

CommonAbstract.php

Lines changed: 58 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
<?php
22
/**
3-
* Common abstract for the common classes package (last modified: 2024.09.20).
3+
* Common abstract for the common classes package (last modified: 2026.03.17).
44
*
55
* This file is a part of the "common classes package", utilised by a number of
66
* packages and projects, including CIDRAM and phpMussel.
@@ -20,7 +20,7 @@ abstract class CommonAbstract
2020
* @var string Common Classes Package tag/release version.
2121
* @link https://github.com/Maikuolan/Common/tags
2222
*/
23-
public const VERSION = '2.12.3';
23+
public const VERSION = '2.16.0';
2424

2525
/**
2626
* Traverse data path.
@@ -33,32 +33,73 @@ abstract class CommonAbstract
3333
*/
3434
public function dataTraverse(&$Data, $Path = [], bool $AllowNonScalar = false, bool $AllowMethodCalls = false)
3535
{
36-
if (!is_array($Path)) {
37-
$Path = preg_split('~(?<!\\\\)\\.~', $Path) ?: [];
36+
if (!\is_array($Path)) {
37+
$Path = \preg_split('~(?<!\\\\)\\.~', $Path) ?: [];
3838
}
39-
$Segment = array_shift($Path);
40-
if ($Segment === null || strlen($Segment) === 0) {
41-
return $AllowNonScalar || is_scalar($Data) ? $Data : '';
39+
$Segment = \array_shift($Path);
40+
if ($Segment === null || \strlen($Segment) === 0) {
41+
return $AllowNonScalar || \is_scalar($Data) ? $Data : '';
4242
}
43-
$Segment = str_replace('\.', '.', $Segment);
44-
if (is_array($Data)) {
43+
$Segment = \str_replace('\.', '.', $Segment);
44+
if ($Data instanceof \Maikuolan\Common\LazyArray) {
45+
$Data->trigger();
46+
$Data = $Data->Data;
47+
}
48+
if (\is_array($Data)) {
49+
if (\preg_match('~^(?:keys|flip|pop|shift)\\(\\)$~i', $Segment)) {
50+
$Segment = 'array_' . \substr($Segment, 0, -2);
51+
$Working = $Segment($Data);
52+
return $this->dataTraverse($Working, $Path, $AllowNonScalar, $AllowMethodCalls);
53+
}
4554
return isset($Data[$Segment]) ? $this->dataTraverse($Data[$Segment], $Path, $AllowNonScalar, $AllowMethodCalls) : '';
4655
}
47-
if (is_object($Data)) {
48-
if (property_exists($Data, $Segment)) {
56+
if (\is_object($Data)) {
57+
if (\property_exists($Data, $Segment)) {
4958
return $this->dataTraverse($Data->$Segment, $Path, $AllowNonScalar, $AllowMethodCalls);
5059
}
51-
if ($AllowMethodCalls && method_exists($Data, $Segment)) {
60+
if ($AllowMethodCalls && \method_exists($Data, $Segment)) {
5261
$Working = $Data->{$Segment}(...$Path);
5362
return $this->dataTraverse($Working, [], $AllowNonScalar);
5463
}
5564
}
56-
if (is_string($Data)) {
57-
if (preg_match('~^(?:trim|str(?:tolower|toupper|len))\\(\\)~i', $Segment)) {
58-
$Segment = substr($Segment, 0, -2);
59-
$Data = $Segment($Data);
60-
}
65+
if (
66+
(\is_string($Data) && \preg_match('~^(?:str(?:tolower|toupper|len)|trim)\\(\\)$~i', $Segment)) ||
67+
(\is_numeric($Data) && \preg_match('~^(?:floor|ceil)\\(\\)$~i', $Segment))
68+
) {
69+
$Segment = \substr($Segment, 0, -2);
70+
$Working = $Segment($Data);
71+
return $this->dataTraverse($Working, $Path, $AllowNonScalar, $AllowMethodCalls);
6172
}
6273
return $this->dataTraverse($Data, $Path, $AllowNonScalar, $AllowMethodCalls);
6374
}
75+
76+
/**
77+
* Used to redact sensitive properties from an object's dump.
78+
*
79+
* @return array An object's dumped properties.
80+
*/
81+
public function __debugInfo(): array
82+
{
83+
$Properties = \get_object_vars($this);
84+
85+
/** Attributes available as of PHP >= 8. Properties returned as is for older PHP versions. */
86+
if (!\class_exists('\ReflectionProperty') || !\method_exists('\ReflectionProperty', 'getAttributes')) {
87+
return $Properties;
88+
}
89+
90+
foreach ($Properties as $Property => &$Value) {
91+
$Reflection = new \ReflectionProperty($this, $Property);
92+
$Attributes = $Reflection->getAttributes();
93+
foreach ($Attributes as $Attribute) {
94+
$Name = $Attribute->getName();
95+
if ($Name === 'Maikuolan\Common\Context') {
96+
$Arguments = $Attribute->getArguments();
97+
if (!empty($Arguments['Sensitive'])) {
98+
$Value = $Attribute->newInstance();
99+
}
100+
}
101+
}
102+
}
103+
return $Properties;
104+
}
64105
}

0 commit comments

Comments
 (0)