Passed
Push — master ( 314cee...0f45c2 )
by Matthew
02:18
created

EDeleteAllAction   A

Complexity

Total Complexity 13

Size/Duplication

Total Lines 106
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 40
c 1
b 0
f 0
dl 0
loc 106
rs 10
wmc 13

2 Methods

Rating   Name   Duplication   Size   Complexity  
A getDeletedModels() 0 3 1
C prepareDataProvider() 0 60 12
1
<?php
2
/**
3
 * Created by PhpStorm.
4
 * Date: 2017-12-07
5
 * Time: 03:12
6
 */
7
8
namespace MP\ExtendedApi;
9
10
use Yii;
11
use yii\data\ActiveDataProvider;
12
use yii\db\ActiveQuery;
13
use yii\db\ActiveRecord;
14
use yii\rest\IndexAction;
15
use yii\web\NotFoundHttpException;
16
17
/**
18
 * Class    EDeleteAllAction
19
 * @package MP\ExtendedApi
20
 * @author  Yarmaliuk Mikhail
21
 * @version 1.0
22
 */
23
class EDeleteAllAction extends IndexAction
24
{
25
    /**
26
     * @var string
27
     */
28
    public $filterAttribute = 'filter';
29
30
    /**
31
     * Add custom query condition
32
     *
33
     * @var null|\Closure
34
     */
35
    public $addQuery = null;
36
37
    /**
38
     * Column name
39
     *
40
     * @var null|string
41
     */
42
    public $filterUser = null;
43
44
    /**
45
     * Delete all without condition
46
     *
47
     * @var bool
48
     */
49
    public $hardDelete = false;
50
51
    /**
52
     * @var array
53
     */
54
    private $_deletedModels = [];
55
56
    /**
57
     * Get deleted models
58
     *
59
     * @return array
60
     */
61
    public function getDeletedModels(): array
62
    {
63
        return $this->_deletedModels;
64
    }
65
66
    /**
67
     * @inheritdoc
68
     */
69
    protected function prepareDataProvider()
70
    {
71
        $filter      = Yii::$app->request->get($this->filterAttribute);
72
        $queryParams = Yii::$app->request->getQueryParams();
73
74
        if (!empty($filter)) {
75
            $queryParams[$this->filterAttribute] = json_decode($filter, true);
0 ignored issues
show
Bug introduced by
It seems like $filter can also be of type array; however, parameter $json of json_decode() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

75
            $queryParams[$this->filterAttribute] = json_decode(/** @scrutinizer ignore-type */ $filter, true);
Loading history...
76
        }
77
78
        if (!$this->hardDelete && (empty($queryParams[$this->filterAttribute]) || empty(array_filter($queryParams[$this->filterAttribute])))) {
79
            throw new NotFoundHttpException("Param '{$this->filterAttribute}' cannot be empty");
80
        }
81
82
        Yii::$app->request->setQueryParams($queryParams);
83
84
        $this->prepareDataProvider = function (EDeleteAllAction $action, $filter) {
85
            /** @var ActiveDataProvider $dataProvider */
86
            $dataProvider = call_user_func([$action->dataFilter->searchModel, 'getDataProvider']);
87
            $dataProvider->query->andWhere($filter);
88
89
            if ($this->addQuery) {
90
                call_user_func($this->addQuery, $dataProvider->query);
91
            }
92
93
            if ($this->filterUser) {
94
                $filterUserColumn = is_callable($this->filterUser) ? call_user_func($this->filterUser) : $this->filterUser;
95
96
                if ($filterUserColumn !== null) {
97
                    $dataProvider->query->andWhere([$filterUserColumn => Yii::$app->user->getId()]);
0 ignored issues
show
Bug introduced by
The method getId() does not exist on null. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

97
                    $dataProvider->query->andWhere([$filterUserColumn => Yii::$app->user->/** @scrutinizer ignore-call */ getId()]);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
98
                }
99
            }
100
101
            return $dataProvider;
102
        };
103
104
        if ($this->hardDelete) {
105
            $this->modelClass::deleteAll();
106
        } else {
107
            $dataProvider = parent::prepareDataProvider();
108
            /** @var ActiveQuery $query */
109
            $query = $dataProvider->query;
110
            $query
111
                ->limit(-1)
112
                ->offset(-1)
113
                ->orderBy([]);
114
115
            $countDeleted = 0;
116
117
            foreach ($query->each() as $model) {
118
                /** @var $model ActiveRecord */
119
                if ($model->delete()) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $model->delete() of type false|integer is loosely compared to true; this is ambiguous if the integer can be 0. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For integer values, zero is a special case, in particular the following results might be unexpected:

0   == false // true
0   == null  // true
123 == false // false
123 == null  // false

// It is often better to use strict comparison
0 === false // false
0 === null  // false
Loading history...
120
                    $this->_deletedModels[] = $model;
121
                    $countDeleted++;
122
                }
123
            }
124
        }
125
126
        Yii::$app->response->headers->set('X-Total-Deleted', $countDeleted);
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $countDeleted does not seem to be defined for all execution paths leading up to this point.
Loading history...
127
128
        return;
129
    }
130
}
131