Passed
Push — main ( 1e096a...fd0a18 )
by Thomas
02:25
created

Value::__get()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 11
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 4
CRAP Score 2

Importance

Changes 2
Bugs 0 Features 0
Metric Value
cc 2
eloc 4
c 2
b 0
f 0
nc 2
nop 1
dl 0
loc 11
ccs 4
cts 4
cp 1
crap 2
rs 10
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Conia\Boiler;
6
7
use Conia\Boiler\Exception\RuntimeException;
8
use Symfony\Component\HtmlSanitizer\HtmlSanitizerConfig;
9
use Throwable;
10
11
/** @psalm-api */
12
class Value implements ValueInterface
13
{
14 61
    public function __construct(protected readonly mixed $value)
15
    {
16 61
    }
17
18 36
    public function __toString(): string
19
    {
20 36
        return htmlspecialchars(
21 36
            (string)$this->value,
22 36
            ENT_QUOTES | ENT_SUBSTITUTE,
23 36
            'UTF-8',
24 36
        );
25
    }
26
27 4
    public function __get(string $name): mixed
28
    {
29
        try {
30
            /**
31
             * @psalm-suppress MixedPropertyFetch
32
             *
33
             * Wrapper::wrap checks types
34
             */
35 4
            return Wrapper::wrap($this->value->{$name});
36 2
        } catch (Throwable) {
37 2
            throw new RuntimeException('No such property');
38
        }
39
    }
40
41 3
    public function __set(string $name, mixed $value): void
42
    {
43
        try {
44 3
            $this->value->{$name} = $value;
45
46 1
            return;
47 2
        } catch (Throwable) {
0 ignored issues
show
Unused Code introduced by
catch (\Throwable) is not reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
48 2
            throw new RuntimeException('No such property');
49
        }
50
    }
51
52 13
    public function __call(string $name, array $args): mixed
53
    {
54 13
        if (is_callable([$this->value, $name])) {
55 12
            return Wrapper::wrap($this->value->{$name}(...$args));
56
        }
57
58 1
        throw new RuntimeException('No such method');
59
    }
60
61 3
    public function __invoke(mixed ...$args): mixed
62
    {
63 3
        if (is_callable($this->value)) {
64 2
            return Wrapper::wrap(($this->value)(...$args));
65
        }
66
67 1
        throw new RuntimeException('No such method');
68
    }
69
70 12
    public function unwrap(): mixed
71
    {
72 12
        return $this->value;
73
    }
74
75 1
    public function strip(array|string|null $allowed = null): string
76
    {
77
        /**
78
         * As of now (early 2023), psalm does not support the
79
         * type array as arguments to strip_tags's $allowed_tags.
80
         *
81
         * @psalm-suppress PossiblyInvalidArgument
82
         */
83 1
        return strip_tags((string)$this->value, $allowed);
84
    }
85
86 4
    public function clean(
87
        HtmlSanitizerConfig $config = null,
88
        bool $removeEmptyLines = true
89
    ): string {
90 4
        return Sanitizer::clean((string)$this->value, $config, $removeEmptyLines);
91
    }
92
93 2
    public function empty(): bool
94
    {
95 2
        return empty($this->value);
96
    }
97
}
98