Passed
Push — flex ( 91a41f )
by MusikAnimal
07:11
created

TopEditsController::indexAction()   A

Complexity

Conditions 4
Paths 3

Size

Total Lines 22
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 4
eloc 14
nc 3
nop 0
dl 0
loc 22
rs 9.7998
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace App\Controller;
6
7
use App\Helper\AutomatedEditsHelper;
8
use App\Model\TopEdits;
9
use App\Repository\TopEditsRepository;
10
use Symfony\Component\HttpFoundation\JsonResponse;
11
use Symfony\Component\HttpFoundation\Response;
12
use Symfony\Component\Routing\Annotation\Route;
13
14
/**
15
 * The Top Edits tool.
16
 */
17
class TopEditsController extends XtoolsController
18
{
19
    /**
20
     * @inheritDoc
21
     * @codeCoverageIgnore
22
     */
23
    public function getIndexRoute(): string
24
    {
25
        return 'TopEdits';
26
    }
27
28
    /**
29
     * @inheritDoc
30
     * @codeCoverageIgnore
31
     */
32
    public function tooHighEditCountRoute(): string
33
    {
34
        return $this->getIndexRoute();
35
    }
36
37
    /**
38
     * The Top Edits by page action is exempt from the edit count limitation.
39
     * @inheritDoc
40
     * @codeCoverageIgnore
41
     */
42
    public function tooHighEditCountActionAllowlist(): array
43
    {
44
        return ['singlePageTopEdits'];
45
    }
46
47
    /**
48
     * @inheritDoc
49
     * @codeCoverageIgnore
50
     */
51
    public function restrictedApiActions(): array
52
    {
53
        return ['namespaceTopEditsUserApi'];
54
    }
55
56
    /**
57
     * Display the form.
58
     * @Route("/topedits", name="topedits")
59
     * @Route("/topedits", name="TopEdits")
60
     * @Route("/topedits/index.php", name="TopEditsIndex")
61
     * @Route("/topedits/{project}", name="TopEditsProject")
62
     * @return Response
63
     */
64
    public function indexAction(): Response
65
    {
66
        // Redirect if at minimum project and username are provided.
67
        if (isset($this->params['project']) && isset($this->params['username'])) {
68
            if (empty($this->params['page'])) {
69
                return $this->redirectToRoute('TopEditsResultNamespace', $this->params);
70
            }
71
            return $this->redirectToRoute('TopEditsResultPage', $this->params);
72
        }
73
74
        return $this->render('topedits/index.html.twig', array_merge([
75
            'xtPageTitle' => 'tool-topedits',
76
            'xtSubtitle' => 'tool-topedits-desc',
77
            'xtPage' => 'TopEdits',
78
79
            // Defaults that will get overriden if in $params.
80
            'namespace' => 0,
81
            'page' => '',
82
            'username' => '',
83
            'start' => '',
84
            'end' => '',
85
        ], $this->params, ['project' => $this->project]));
86
    }
87
88
    /**
89
     * Every action in this controller (other than 'index') calls this first.
90
     * @param TopEditsRepository $topEditsRepo
91
     * @param AutomatedEditsHelper $autoEditsHelper
92
     * @return TopEdits
93
     * @codeCoverageIgnore
94
     */
95
    public function setUpTopEdits(TopEditsRepository $topEditsRepo, AutomatedEditsHelper $autoEditsHelper): TopEdits
96
    {
97
        return new TopEdits(
98
            $topEditsRepo,
99
            $autoEditsHelper,
100
            $this->project,
101
            $this->user,
0 ignored issues
show
Bug introduced by
It seems like $this->user can also be of type null; however, parameter $user of App\Model\TopEdits::__construct() does only seem to accept App\Model\User, 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

101
            /** @scrutinizer ignore-type */ $this->user,
Loading history...
102
            $this->page,
103
            $this->namespace,
104
            $this->start,
105
            $this->end,
106
            $this->limit,
107
            (int)$this->request->query->get('pagination', 0)
108
        );
109
    }
110
111
    /**
112
     * List top edits by this user for all pages in a particular namespace.
113
     * @Route("/topedits/{project}/{username}/{namespace}/{start}/{end}",
114
     *     name="TopEditsResultNamespace",
115
     *     requirements={
116
     *         "username" = "(ipr-.+\/\d+[^\/])|([^\/]+)",
117
     *         "namespace"="|all|\d+",
118
     *         "start"="|\d{4}-\d{2}-\d{2}",
119
     *         "end"="|\d{4}-\d{2}-\d{2}",
120
     *     },
121
     *     defaults={"namespace" = "all", "start"=false, "end"=false}
122
     * )
123
     * @param TopEditsRepository $topEditsRepo
124
     * @param AutomatedEditsHelper $autoEditsHelper
125
     * @return Response
126
     * @codeCoverageIgnore
127
     */
128
    public function namespaceTopEditsAction(
129
        TopEditsRepository $topEditsRepo,
130
        AutomatedEditsHelper $autoEditsHelper
131
    ): Response {
132
        // Max number of rows per namespace to show. `null` here will use the TopEdits default.
133
        $this->limit = $this->isSubRequest ? 10 : $this->limit;
134
135
        $topEdits = $this->setUpTopEdits($topEditsRepo, $autoEditsHelper);
136
        $topEdits->prepareData();
137
138
        $ret = [
139
            'xtPage' => 'TopEdits',
140
            'xtTitle' => $this->user->getUsername(),
0 ignored issues
show
Bug introduced by
The method getUsername() 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

140
            'xtTitle' => $this->user->/** @scrutinizer ignore-call */ getUsername(),

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...
141
            'te' => $topEdits,
142
            'is_sub_request' => $this->isSubRequest,
143
        ];
144
145
        // Output the relevant format template.
146
        return $this->getFormattedResponse('topedits/result_namespace', $ret);
147
    }
148
149
    /**
150
     * List top edits by this user for a particular page.
151
     * @Route("/topedits/{project}/{username}/{namespace}/{page}/{start}/{end}",
152
     *     name="TopEditsResultPage",
153
     *     requirements={
154
     *         "username" = "(ipr-.+\/\d+[^\/])|([^\/]+)",
155
     *         "namespace"="|all|\d+",
156
     *         "page"="(.+?)(?!\/(?:|\d{4}-\d{2}-\d{2})(?:\/(|\d{4}-\d{2}-\d{2}))?)?$",
157
     *         "start"="|\d{4}-\d{2}-\d{2}",
158
     *         "end"="|\d{4}-\d{2}-\d{2}",
159
     *     },
160
     *     defaults={"namespace"="all", "start"=false, "end"=false}
161
     * )
162
     * @param TopEditsRepository $topEditsRepo
163
     * @param AutomatedEditsHelper $autoEditsHelper
164
     * @return Response
165
     * @codeCoverageIgnore
166
     * @todo Add pagination.
167
     */
168
    public function singlePageTopEditsAction(
169
        TopEditsRepository $topEditsRepo,
170
        AutomatedEditsHelper $autoEditsHelper
171
    ): Response {
172
        $topEdits = $this->setUpTopEdits($topEditsRepo, $autoEditsHelper);
173
        $topEdits->prepareData();
174
175
        // Send all to the template.
176
        return $this->getFormattedResponse('topedits/result_article', [
177
            'xtPage' => 'TopEdits',
178
            'xtTitle' => $this->user->getUsername() . ' - ' . $this->page->getTitle(),
0 ignored issues
show
Bug introduced by
The method getTitle() 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

178
            'xtTitle' => $this->user->getUsername() . ' - ' . $this->page->/** @scrutinizer ignore-call */ getTitle(),

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...
179
            'te' => $topEdits,
180
        ]);
181
    }
182
183
    /************************ API endpoints ************************/
184
185
    /**
186
     * List top edits by this user for all pages in a particular namespace.
187
     * @Route("/api/user/top_edits/{project}/{username}/{namespace}/{start}/{end}",
188
     *     name="UserApiTopEditsNamespace",
189
     *     requirements={
190
     *         "username" = "(ipr-.+\/\d+[^\/])|([^\/]+)",
191
     *         "namespace"="|\d+|all",
192
     *         "start"="|\d{4}-\d{2}-\d{2}",
193
     *         "end"="|\d{4}-\d{2}-\d{2}",
194
     *     },
195
     *     defaults={"namespace"="all", "start"=false, "end"=false}
196
     * )
197
     * @param TopEditsRepository $topEditsRepo
198
     * @param AutomatedEditsHelper $autoEditsHelper
199
     * @return JsonResponse
200
     * @codeCoverageIgnore
201
     */
202
    public function namespaceTopEditsUserApiAction(
203
        TopEditsRepository $topEditsRepo,
204
        AutomatedEditsHelper $autoEditsHelper
205
    ): JsonResponse {
206
        $this->recordApiUsage('user/topedits');
207
208
        $topEdits = $this->setUpTopEdits($topEditsRepo, $autoEditsHelper);
209
        $topEdits->prepareData();
210
211
        return $this->getFormattedApiResponse([
212
            'top_edits' => (object)$topEdits->getTopEdits(),
213
        ]);
214
    }
215
216
    /**
217
     * Get the all edits of a user to a specific page, maximum 1000.
218
     * @Route("/api/user/top_edits/{project}/{username}/{namespace}/{page}/{start}/{end}",
219
     *     name="UserApiTopEditsPage",
220
     *     requirements = {
221
     *         "username" = "(ipr-.+\/\d+[^\/])|([^\/]+)",
222
     *         "namespace"="|\d+|all",
223
     *         "page"="(.+?)(?!\/(?:|\d{4}-\d{2}-\d{2})(?:\/(|\d{4}-\d{2}-\d{2}))?)?$",
224
     *         "start"="|\d{4}-\d{2}-\d{2}",
225
     *         "end"="|\d{4}-\d{2}-\d{2}",
226
     *     },
227
     *     defaults={"namespace"="all", "start"=false, "end"=false}
228
     * )
229
     * @param TopEditsRepository $topEditsRepo
230
     * @param AutomatedEditsHelper $autoEditsHelper
231
     * @return JsonResponse
232
     * @codeCoverageIgnore
233
     * @todo Add pagination.
234
     */
235
    public function singlePageTopEditsUserApiAction(
236
        TopEditsRepository $topEditsRepo,
237
        AutomatedEditsHelper $autoEditsHelper
238
    ): JsonResponse {
239
        $this->recordApiUsage('user/topedits');
240
241
        $topEdits = $this->setUpTopEdits($topEditsRepo, $autoEditsHelper);
242
        $topEdits->prepareData(false);
243
244
        return $this->getFormattedApiResponse([
245
            'top_edits' => $topEdits->getTopEdits(),
246
        ]);
247
    }
248
}
249