Completed
Push — master ( b511be...229cbe )
by Song
02:32
created

HandleController::handleAction()   B

Complexity

Conditions 6
Paths 14

Size

Total Lines 32

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 6
nc 14
nop 1
dl 0
loc 32
rs 8.7857
c 0
b 0
f 0
1
<?php
2
3
namespace Encore\Admin\Controllers;
4
5
use Encore\Admin\Actions\Action;
6
use Encore\Admin\Actions\GridAction;
7
use Encore\Admin\Actions\Response;
8
use Encore\Admin\Actions\RowAction;
9
use Encore\Admin\Widgets\Form;
10
use Encore\Admin\Widgets\Selectable\Selectable;
11
use Exception;
12
use Illuminate\Contracts\Support\Renderable;
13
use Illuminate\Database\Eloquent\Model;
14
use Illuminate\Http\Request;
15
use Illuminate\Routing\Controller;
16
use Illuminate\Support\Collection;
17
18
class HandleController extends Controller
19
{
20
    /**
21
     * @param Request $request
22
     *
23
     * @return $this|mixed
24
     */
25
    public function handleForm(Request $request)
26
    {
27
        $form = $this->resolveForm($request);
28
29
        if ($errors = $form->validate($request)) {
30
            return back()->withInput()->withErrors($errors);
31
        }
32
33
        return $form->sanitize()->handle($request);
34
    }
35
36
    /**
37
     * @param Request $request
38
     *
39
     * @throws Exception
40
     *
41
     * @return Form
42
     */
43 View Code Duplication
    protected function resolveForm(Request $request)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
44
    {
45
        if (!$request->has('_form_')) {
46
            throw new Exception('Invalid form request.');
47
        }
48
49
        $formClass = $request->get('_form_');
50
51
        if (!class_exists($formClass)) {
52
            throw new Exception("Form [{$formClass}] does not exist.");
53
        }
54
55
        /** @var Form $form */
56
        $form = app($formClass);
57
58
        if (!method_exists($form, 'handle')) {
59
            throw new Exception("Form method {$formClass}::handle() does not exist.");
60
        }
61
62
        return $form;
63
    }
64
65
    /**
66
     * @param Request $request
67
     *
68
     * @return $this|\Illuminate\Http\JsonResponse
69
     */
70
    public function handleAction(Request $request)
71
    {
72
        $action = $this->resolveActionInstance($request);
73
74
        $model = null;
75
        $arguments = [];
76
77
        if ($action instanceof GridAction) {
78
            $model = $action->retrieveModel($request);
79
            $arguments[] = $model;
80
        }
81
82
        if (!$action->passesAuthorization($model)) {
83
            return $action->failedAuthorization();
84
        }
85
86
        if ($action instanceof RowAction) {
87
            $action->setRow($model);
88
        }
89
90
        try {
91
            $response = $action->validate($request)->handle(
0 ignored issues
show
Bug introduced by
The method handle() does not exist on Encore\Admin\Actions\Action. Did you maybe mean getHandleRoute()?

This check marks calls to methods that do not seem to exist on an object.

This is most likely the result of a method being renamed without all references to it being renamed likewise.

Loading history...
92
                ...$this->resolveActionArgs($request, ...$arguments)
0 ignored issues
show
Documentation introduced by
$arguments is of type array, but the function expects a object<Illuminate\Databa...ollection>|boolean|null.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
93
            );
94
        } catch (Exception $exception) {
95
            return Response::withException($exception)->send();
96
        }
97
98
        if ($response instanceof Response) {
99
            return $response->send();
100
        }
101
    }
102
103
    /**
104
     * @param Request $request
105
     *
106
     * @throws Exception
107
     *
108
     * @return Action
109
     */
110 View Code Duplication
    protected function resolveActionInstance(Request $request)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
111
    {
112
        if (!$request->has('_action')) {
113
            throw new Exception('Invalid action request.');
114
        }
115
116
        $actionClass = str_replace('_', '\\', $request->get('_action'));
117
118
        if (!class_exists($actionClass)) {
119
            throw new Exception("Form [{$actionClass}] does not exist.");
120
        }
121
122
        /** @var GridAction $form */
123
        $action = app($actionClass);
124
125
        if (!method_exists($action, 'handle')) {
126
            throw new Exception("Action method {$actionClass}::handle() does not exist.");
127
        }
128
129
        return $action;
130
    }
131
132
    /**
133
     * @param Request               $request
134
     * @param Model|Collection|bool $model
135
     *
136
     * @return array
137
     */
138
    protected function resolveActionArgs(Request $request, $model = null)
139
    {
140
        $args = [$request];
141
142
        if (!empty($model)) {
143
            array_unshift($args, $model);
144
        }
145
146
        return $args;
147
    }
148
149
    /**
150
     * @param Request $request
151
     * @return mixed|string|string[]
152
     */
153 View Code Duplication
    public function handleSelectable(Request $request)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
154
    {
155
        $class = $request->get('selectable');
156
        $multiple = $request->get('multiple', 0);
157
158
        $class = str_replace('_', '\\', $class);
159
160
        if (class_exists($class)) {
161
            /** @var Selectable $selectable */
162
            $selectable = new $class();
163
164
            return $selectable->render($multiple);
165
        }
166
167
        return $class;
168
    }
169
170
    /**
171
     * @param Request $request
172
     * @return mixed|string|string[]
173
     */
174 View Code Duplication
    public function handleRenderable(Request $request)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
175
    {
176
        $class = $request->get('renderable');
177
        $key   = $request->get('key');
178
179
        $class = str_replace('_', '\\', $class);
180
181
        if (class_exists($class)) {
182
            /** @var Renderable $selectable */
183
            $renderable = new $class();
184
185
            return $renderable->render($key);
186
        }
187
188
        return $class;
189
    }
190
}
191