• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

The-oGlow / ezkoding / 35610251881

21 Sep 2026 01:56PM UTC coverage: 85.553%. Remained the same
35610251881

push

github

web-flow
Merge pull request #13 from The-oGlow/develop

Develop

169 of 205 new or added lines in 16 files covered. (82.44%)

65 existing lines in 10 files now uncovered.

681 of 796 relevant lines covered (85.55%)

7.47 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

85.71
/src/Tools/String/ImplodeTrait.php
1
<?php
2

3
declare(strict_types=1);
4

5
/*
6
 * This file is part of ezkoding
7
 *
8
 * (c) 2025 Oliver Glowa, coding.glowa.com
9
 *
10
 * This source file is subject to the Apache-2.0 license that is bundled
11
 * with this source code in the file LICENSE.
12
 */
13

14
namespace ollily\Tools\String;
15

16
use ArrayAccess;
17
use Stringable;
18

19
trait ImplodeTrait
20
{
21
    /**
22
     * Default glue character.
23
     *
24
     * @see ImplodeTrait::array_flatten()
25
     * @see ImplodeTrait::implode_recursive()
26
     */
27
    public const string DEFAULT_GLUE = ',';
28

29
    /**
30
     * Default separate character for csv.
31
     *
32
     * @see ImplodeTrait::array_flatten()
33
     * @see ImplodeTrait::implode_recursive()
34
     */
35
    public const string DEFAULT_ITEM_SEP = ';';
36

37
    /**
38
     * Recursively implodes an array with optional key inclusion.
39
     *
40
     * @param string $glue        value that glues elements together
41
     * @param mixed  $anyData     multi-dimensional array to recursively implode
42
     * @param bool   $withTextSep add a text seperator (") around each value of a scalar type (default: false)
43
     * @param bool   $withKeys    include keysForValue before their values (default: false)
44
     *
45
     * @return string imploded array
46
     *
47
     * @see https://www.php.net/manual/en/language.types.type-system.php
48
     */
49
    // @phpcs:ignore PSR1.Methods.CamelCapsMethodName.NotCamelCaps
50
    final public static function implode_recursive(string $glue, mixed $anyData, bool $withTextSep = false, bool $withKeys = false): string // NOSONAR: php:S100
3 ✔
51
    {
52
        $output   = '';
3 ✔
53
        $valueIdx = 0;
3 ✔
54
        $textSep  = $withTextSep ? '"' : '';
3 ✔
55
        $objWithArray = (is_object($anyData) && is_subclass_of($anyData, ArrayAccess::class));
3 ✔
56

57
        if (is_array($anyData) || $objWithArray) {
3 ✔
58
            foreach ($anyData as $key => $value) { // @phpstan-ignore foreach.nonIterable
3 ✔
59
                $currKey = ($withKeys ? (is_int($key) ? $key : "'$key'") . '=>' : ''); // NOSONAR: php:S3358
3 ✔
60
                $output .= ($valueIdx > 0 ? $glue : '') .  $currKey;
3 ✔
61

62
                if (is_array($value)) {
3 ✔
63
                    $arrOutput = self::implode_recursive($glue, $value, $withTextSep, $withKeys);
1 ✔
64
                    if (!empty($arrOutput)) {
1 ✔
65
                        $output .= '[' . $arrOutput . ']';
1 ✔
66
                    } else {
UNCOV
67
                        $output .= '[]';
×
68
                    }
69
                } else {
70
                    if (is_object($value)) {
3 ✔
71
                        $objOutput = self::implode_recursive($glue, $value, $withTextSep, $withKeys);
1 ✔
72
                        if (!empty($objOutput)) {
1 ✔
73
                            $output .= '{' . $objOutput . '}';
1 ✔
74
                        } else {
UNCOV
75
                            $output .= '{}';
×
76
                        }
77
                    } else {
78
                        $output .= $textSep . ((string) $value) . $textSep;
2 ✔
79
                    }
80
                }
81
                $valueIdx++;
3 ✔
82
            }
83
        } else {
84
            if (is_object($anyData)) {
1 ✔
85
                if ($anyData instanceof Stringable) {
1 ✔
UNCOV
86
                    $output = $anyData->__toString();
×
87
                } else {
88
                    $output = $anyData::class;
1 ✔
89
                }
90
            } else {
UNCOV
91
                $output = $anyData;
×
92
            }
93
        }
94

95
        return $output;
3 ✔
96
    }
97

98
    /**
99
     * Flatten a multidimensional anyData to one dimension, optionally preserving keys.
100
     * Original found on {@link https://stackoverflow.com/a/526633}.
101
     *
102
     * @param array<mixed> $anyData      the anyData to flatten
103
     * @param int          $preserveKeys 0 to not preserve keys (default),
104
     *                                   1 to preserve string keys only,
105
     *                                   2 to preserve all keys
106
     * @param array<mixed> $output       internal use argument for recursion
107
     *
108
     * @return array<mixed>
109
     *
110
     * @see https://stackoverflow.com/a/526633
111
     */
112
    // @phpcs:ignore PSR1.Methods.CamelCapsMethodName.NotCamelCaps
113
    final public function array_flatten(array $anyData, int $preserveKeys = 0, array &$output = []): array // NOSONAR: php:S100
4 ✔
114
    {
115
        foreach ($anyData as $anyKey => $anyValue) {
4 ✔
116
            if (is_array($anyValue)) {
3 ✔
117
                $output = $this->array_flatten($anyValue, $preserveKeys, $output);
2 ✔
118
            } elseif ($preserveKeys + (int)is_string($anyKey) > 1) {
3 ✔
UNCOV
119
                $output[$anyKey] = $anyValue;
×
120
            } else {
121
                $output[] = $anyValue;
3 ✔
122
            }
123
        }
124

125
        return $output;
4 ✔
126
    }
127
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc