Completed
Push — master ( 127a36...4996f5 )
by Andrii
04:36
created

src/grid/BillGridView.php (2 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
/**
3
 * Finance module for HiPanel
4
 *
5
 * @link      https://github.com/hiqdev/hipanel-module-finance
6
 * @package   hipanel-module-finance
7
 * @license   BSD-3-Clause
8
 * @copyright Copyright (c) 2015-2019, HiQDev (http://hiqdev.com/)
9
 */
10
11
namespace hipanel\modules\finance\grid;
12
13
use hipanel\grid\CurrencyColumn;
14
use hipanel\grid\MainColumn;
15
use hipanel\helpers\StringHelper;
16
use hipanel\helpers\Url;
17
use hipanel\modules\finance\logic\bill\QuantityFormatterFactoryInterface;
18
use hipanel\modules\finance\menus\BillActionsMenu;
19
use hipanel\modules\finance\models\Bill;
20
use hipanel\modules\finance\models\Charge;
21
use hipanel\modules\finance\widgets\BillType;
22
use hipanel\modules\finance\widgets\BillTypeFilter;
23
use hipanel\modules\finance\widgets\ColoredBalance;
24
use hipanel\modules\finance\widgets\LinkToObjectResolver;
25
use hipanel\widgets\ArraySpoiler;
26
use hiqdev\yii2\menus\grid\MenuColumn;
27
use Yii;
28
use yii\helpers\Html;
29
30
/**
31
 * Class BillGridView.
32
 *
33
 * @author Dmytro Naumenko <[email protected]>
34
 */
35
class BillGridView extends \hipanel\grid\BoxedGridView
36
{
37
    /**
38
     * @var QuantityFormatterFactoryInterface
39
     */
40
    private $quantityFactory;
41
42
    public function __construct(QuantityFormatterFactoryInterface $quantityFactory, array $config = [])
43
    {
44
        parent::__construct($config);
45
46
        $this->quantityFactory = $quantityFactory;
47
    }
48
49
    public $currencies = [];
50
51
    public function columns()
52
    {
53
        return array_merge(parent::columns(), [
54
            'bill' => [
55
                'class' => MainColumn::class,
56
                'attribute' => 'bill',
57
                'filterAttribute' => 'bill_like',
58
            ],
59
            'time' => [
60
                'format' => 'html',
61
                'filter' => false,
62
                'label' => Yii::t('hipanel', 'Time'),
63
                'sortAttribute' => 'no',
64
                'contentOptions' => ['class' => 'text-nowrap'],
65
                'value' => function (Bill $model) {
66
                    list($date, $time) = explode(' ', $model->time, 2);
67
68
                    return in_array($model->gtype, [
69
                        'discount',
70
                        'domain',
71
                        'monthly',
72
                        'overuse',
73
                        'premium_package',
74
                        'feature',
75
                        'intercept',
76
                        'periodic',
77
                    ], true) && $time === '00:00:00'
78
                        ? Yii::$app->formatter->asDate($date, 'LLLL y')
79
                        : Yii::$app->formatter->asDateTime($model->time);
80
                },
81
            ],
82
            'sum' => [
83
                'class' => CurrencyColumn::class,
84
                'attribute' => 'sum',
85
                'colors' => ['danger' => 'warning'],
86
                'headerOptions' => ['class' => 'text-right'],
87
                'contentOptions' => function (Bill $model) {
88
                    return ['class' => 'text-right' . ($model->sum > 0 ? ' text-bold' : '')];
89
                },
90
            ],
91
            'sum_editable' => [
92
                'class' => CurrencyColumn::class,
93
                'format' => 'raw',
94
                'attribute' => 'sum',
95
                'colors' => ['danger' => 'warning'],
96
                'headerOptions' => ['class' => 'text-right'],
97
                'urlCallback' => function ($model, $key) {
98
                    return Yii::$app->user->can('bill.read')
99
                        ? Url::to(['@bill/view', 'id' => $model->id])
100
                        : null;
101
                },
102
                'contentOptions' => function (Bill $model) {
103
                    return ['class' => 'text-right' . ($model->sum > 0 ? ' text-bold' : '')];
104
                },
105
            ],
106
            'quantity' => [
107
                'format' => 'raw',
108
                'headerOptions' => ['class' => 'text-right'],
109
                'contentOptions' => ['class' => 'text-right text-bold'],
110
                'value' => function (Bill $bill) {
111
                    return $this->formatQuantity($bill);
112
                },
113
            ],
114
            'balance' => [
115
                'attribute' => 'balance',
116
                'format' => 'raw',
117
                'headerOptions' => ['class' => 'text-right'],
118
                'contentOptions' => function ($model, $key, $index) {
119
                    return ['class' => 'text-right' . ($index ? '' : ' text-bold')];
120
                },
121
                'value' => function (Bill $model) {
122
                    return ColoredBalance::widget(compact('model'));
123
                },
124
                'filterAttribute' => 'currency_in',
125
                'filterOptions' => ['class' => 'narrow-filter'],
126
                'filter' => function ($column, $filterModel) {
127
                    $currencies = array_combine(array_keys($this->currencies), array_map(function ($k) {
128
                        return StringHelper::getCurrencySymbol($k);
129
                    }, array_keys($this->currencies)));
130
131
                    return Html::activeDropDownList($filterModel, 'currency_in', $currencies, ['class' => 'form-control', 'prompt' => '--']);
132
                },
133
            ],
134
            'gtype' => [
135
                'attribute' => 'gtype',
136
            ],
137
            'type_label' => [
138
                'filter' => function ($column, $filterModel) {
139
                    return BillTypeFilter::widget([
140
                        'options' => ['class' => 'form-control text-right', 'style' => 'max-width: 12em'],
141
                        'attribute' => 'ftype',
142
                        'model' => $filterModel,
143
                    ]);
144
                },
145
                'sortAttribute' => 'type',
146
                'format' => 'raw',
147
                'headerOptions' => ['class' => 'text-right'],
148
                'contentOptions' => function (Bill $model) {
149
                    return ['class' => 'text-right'];
150
                },
151
                'value' => function (Bill $model) {
152
                    return BillType::widget([
153
                        'model' => $model,
154
                        'field' => 'ftype',
155
                        'labelField' => 'type_label',
156
                    ]);
157
                },
158
            ],
159
            'description' => [
160
                'attribute' => 'descr',
161
                'format' => 'raw',
162
                'value' => function (Bill $model) {
163
                    $descr = $model->descr ?: $model->label;
164
                    $text = mb_strlen($descr) > 70 ? ArraySpoiler::widget(['data' => $descr]) : $descr;
165
                    $tariff = $model->tariff ? Html::tag('span',
166
                        Yii::t('hipanel', 'Tariff') . ': ' . Html::a($model->tariff,
0 ignored issues
show
The property tariff does not exist on object<hipanel\modules\finance\models\Bill>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
167
                            ['@plan/view', 'id' => $model->tariff_id]), ['class' => 'pull-right']) : '';
0 ignored issues
show
The property tariff_id does not exist on object<hipanel\modules\finance\models\Bill>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
168
                    $amount = $this->formatQuantity($model);
169
                    $object = $this->objectTag($model);
170
171
                    return $tariff . $amount . ' ' . implode('<br>', array_filter([$object, $text]));
172
                },
173
            ],
174
            'tariff_link' => [
175
                'attribute' => 'tariff',
176
                'format' => 'html',
177
                'value' => function (Bill $model) {
178
                    return $this->tariffLink($model);
179
                },
180
            ],
181
            'object' => [
182
                'attribute' => 'object',
183
                'format' => 'html',
184
                'value' => function (Bill $model) {
185
                    return $this->objectTag($model);
186
                },
187
            ],
188
            'actions' => [
189
                'class' => MenuColumn::class,
190
                'menuClass' => BillActionsMenu::class,
191
            ],
192
            'common_object_link' => [
193
                'format' => 'html',
194
                'value' => function (Charge $model) {
195
                    $link = LinkToObjectResolver::widget([
196
                        'model'          => $model->commonObject,
197
                        'labelAttribute' => 'name',
198
                        'idAttribute'    => 'id',
199
                        'typeAttribute'  => 'type',
200
                        'customLinks' => [
201
                            'part' => '@server/view',
202
                        ],
203
                    ]);
204
205
                    return $link;
206
                },
207
            ],
208
        ]);
209
    }
210
211
    public function tariffLink($model): string
212
    {
213
        return Html::a($model->tariff, ['@plan/view', 'id' => $model->tariff_id]);
214
    }
215
216
    public function objectTag($model): string
217
    {
218
        return $model->object ? implode(':&nbsp;', [$model->class_label, $this->objectLink($model)]) : '';
219
    }
220
221
    /**
222
     * Creates link to object details page.
223
     *
224
     * @param Bill $model
225
     * @return string
226
     */
227
    public function objectLink(Bill $model): string
228
    {
229
        return $model->class === 'device'
230
            ? Html::a($model->object, ['@server/view', 'id' => $model->object_id])
231
            : Html::tag('b', $model->object);
232
    }
233
234
    private function formatQuantity(Bill $bill): string
235
    {
236
        $billQty = $this->quantityFactory->forBill($bill);
237
238
        if ($billQty !== null) {
239
            return Html::tag('nobr', Html::tag('b', $billQty->format()));
240
        }
241
242
        return '';
243
    }
244
}
245