Issues (12)

src/Models/MoneyCast.php (2 issues)

1
<?php
2
3
namespace ByTIC\Money\Models;
4
5
use ByTIC\DataObjects\BaseDto;
6
use ByTIC\DataObjects\Casts\CastsAttributes;
7
use ByTIC\Money\Money;
8
use InvalidArgumentException;
9
use Money\Currency;
10
11
/**
12
 * Class MoneyCast
13
 * @package ByTIC\Money\Models
14
 */
15
class MoneyCast implements CastsAttributes
16
{
17
18
    /**
19
     * The currency code or the model attribute holding the currency code.
20
     *
21
     * @var string|null
22
     */
23
    protected $currency;
24
25
    /**
26
     * Set if the storing is done as decimal or integer
27
     *
28
     * @var string|null
29
     */
30
    protected $parser = 'decimal';
31
32
    /**
33
     * Instantiate the class.
34
     *
35
     * @param string|null $currency
36
     */
37
    public function __construct(string $currency = null, string $parser = 'decimal')
38
    {
39
        $this->currency = $currency;
40
41
        if (!in_array($parser, ['decimal', 'integer'])) {
42
            throw new InvalidArgumentException(
43
                sprintf('Invalid value provided for parser in %s::$%s', get_class($model), $parser)
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $model seems to be never defined.
Loading history...
44
            );
45
        }
46
        $this->parser = $parser;
47
    }
48
49
    /**
50
     * Transform the attribute from the underlying model values.
51
     *
52
     * @param BaseDto $model
53
     * @param string $key
54
     * @param mixed $value
55
     * @param array $attributes
56
     *
57
     * @return Money|null
58
     */
59
    public function get($model, string $key, $value, array $attributes)
60
    {
61
        if ($value === null) {
62
            return null;
63
        }
64
        return $this->transformToMoney($value, $attributes);
65
    }
66
67
    /**
68
     * Transform the attribute to its underlying model values.
69
     *
70
     * @param \Illuminate\Database\Eloquent\Model $model
0 ignored issues
show
The type Illuminate\Database\Eloquent\Model was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
71
     * @param string $key
72
     * @param mixed $value
73
     * @param array $attributes
74
     *
75
     * @return array
76
     * @throws \InvalidArgumentException
77
     *
78
     */
79
    public function set($model, string $key, $value, array $attributes)
80
    {
81
        if ($value === null) {
82
            return [$key => $value];
83
        }
84
85
        try {
86
            $money = $this->transformToMoney($value, $attributes);
87
        } catch (InvalidArgumentException $e) {
88
            throw new InvalidArgumentException(
89
                sprintf('Invalid data provided for %s::$%s', get_class($model), $key)
90
            );
91
        }
92
93
        $amount = $this->parser == 'decimal' ? $money->formatByDecimal(Money::getCurrencies()) : $money->getAmount();
94
95
        if (array_key_exists($this->currency, $attributes)) {
96
            return [$key => $amount, $this->currency => $money->getCurrency()->getCode()];
97
        }
98
99
        return [$key => $amount];
100
    }
101
102
    /**
103
     * @param $value
104
     * @param $attributes
105
     * @return Money
106
     */
107
    protected function transformToMoney($value, $attributes): Money
108
    {
109
        if ($this->parser == 'decimal') {
110
            return Money::parseByDecimal(
111
                $value,
112
                $this->getCurrency($attributes),
113
                Money::getCurrencies()
114
            );
115
        }
116
117
        return Money::parse(
118
            $value,
119
            $this->getCurrency($attributes)
120
        );
121
    }
122
123
    /**
124
     * Retrieve the money.
125
     *
126
     * @param array $attributes
127
     *
128
     * @return \Money\Currency
129
     */
130
    protected function getCurrency(array $attributes)
131
    {
132
        $defaultCode = Money::currencyDefault();
133
134
        if ($this->currency === null) {
135
            return new Currency($defaultCode);
136
        }
137
138
        $currency = new Currency($this->currency);
139
        $currencies = Money::getCurrencies();
140
141
        if ($currencies->contains($currency)) {
142
            return $currency;
143
        }
144
145
        $code = $attributes[$this->currency] ?? $defaultCode;
146
147
        return new Currency($code);
148
    }
149
}