Passed
Pull Request — 1.11.x (#4900)
by Angel Fernando Quiroz
11:12
created

findResults()   C

Complexity

Conditions 10
Paths 192

Size

Total Lines 75
Code Lines 41

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 41
dl 0
loc 75
rs 6.9
c 1
b 0
f 0
cc 10
nc 192
nop 3

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
/* For licensing terms, see /license.txt */
4
5
use Chamilo\CoreBundle\Entity\TrackEAttempt;
6
use Chamilo\CoreBundle\Entity\TrackEExercises;
7
use Chamilo\CourseBundle\Entity\CQuiz;
8
use Chamilo\PluginBundle\ExerciseFocused\Entity\Log as FocusedLog;
9
use Chamilo\PluginBundle\ExerciseMonitoring\Entity\Log as MonitoringLog;
10
use Chamilo\UserBundle\Entity\User;
11
use Doctrine\ORM\EntityManagerInterface;
12
use Doctrine\ORM\Query\Expr\Join;
13
use Symfony\Component\HttpFoundation\Request as HttpRequest;
0 ignored issues
show
Bug introduced by
This use statement conflicts with another class in this namespace, HttpRequest. Consider defining an alias.

Let?s assume that you have a directory layout like this:

.
|-- OtherDir
|   |-- Bar.php
|   `-- Foo.php
`-- SomeDir
    `-- Foo.php

and let?s assume the following content of Bar.php:

// Bar.php
namespace OtherDir;

use SomeDir\Foo; // This now conflicts the class OtherDir\Foo

If both files OtherDir/Foo.php and SomeDir/Foo.php are loaded in the same runtime, you will see a PHP error such as the following:

PHP Fatal error:  Cannot use SomeDir\Foo as Foo because the name is already in use in OtherDir/Foo.php

However, as OtherDir/Foo.php does not necessarily have to be loaded and the error is only triggered if it is loaded before OtherDir/Bar.php, this problem might go unnoticed for a while. In order to prevent this error from surfacing, you must import the namespace with a different alias:

// Bar.php
namespace OtherDir;

use SomeDir\Foo as SomeDirFoo; // There is no conflict anymore.
Loading history...
14
15
require_once __DIR__.'/../../../main/inc/global.inc.php';
16
17
api_protect_course_script(true);
18
19
if (!api_is_allowed_to_edit()) {
20
    api_not_allowed(true);
21
}
22
23
$plugin = ExerciseFocusedPlugin::create();
24
$monitoringPlugin = ExerciseMonitoringPlugin::create();
25
$monitoringPluginIsEnabled = $monitoringPlugin->isEnabled(true);
26
$request = HttpRequest::createFromGlobals();
27
$em = Database::getManager();
28
$focusedLogRepository = $em->getRepository(FocusedLog::class);
29
$attempsRepository = $em->getRepository(TrackEAttempt::class);
30
31
if (!$plugin->isEnabled(true)) {
32
    api_not_allowed(true);
33
}
34
35
$params = $request->query->all();
36
37
$results = findResults($params, $em, $plugin);
38
39
$data = [];
40
41
/** @var array<string, mixed> $result */
42
foreach ($results as $result) {
43
    /** @var TrackEExercises $trackExe */
44
    $trackExe = $result['exe'];
45
    $user = api_get_user_entity($trackExe->getExeUserId());
46
47
    $outfocusedLimitCount = $focusedLogRepository->countByActionInExe($trackExe, FocusedLog::TYPE_OUTFOCUSED_LIMIT);
48
    $timeLimitCount = $focusedLogRepository->countByActionInExe($trackExe, FocusedLog::TYPE_TIME_LIMIT);
49
50
    $exercise = new Exercise($trackExe->getCId());
51
    $exercise->read($trackExe->getExeExoId());
52
53
    $quizType = (int) $exercise->selectType();
54
55
    $data[] = [
56
        get_lang('LoginName'),
57
        $user->getUsername(),
58
    ];
59
    $data[] = [
60
        get_lang('Student'),
61
        $user->getFirstname(),
62
        $user->getLastname(),
63
    ];
64
65
    if ($monitoringPluginIsEnabled
66
        && 'true' === $monitoringPlugin->get(ExerciseMonitoringPlugin::SETTING_INSTRUCTION_AGE_DISTINCTION_ENABLE)
67
    ) {
68
        $fieldVariable = $monitoringPlugin->get(ExerciseMonitoringPlugin::SETTING_EXTRAFIELD_BIRTHDATE);
69
        $birthdateValue = UserManager::get_extra_user_data_by_field($user->getId(), $fieldVariable);
70
71
        $data[] = [
72
            $monitoringPlugin->get_lang('Birthdate'),
73
            $birthdateValue ? $birthdateValue[$fieldVariable] : '----',
74
            $monitoringPlugin->isAdult($user->getId())
75
                ? $monitoringPlugin->get_lang('AdultStudent')
76
                : $monitoringPlugin->get_lang('MinorStudent'),
77
        ];
78
    }
79
80
    if ($trackExe->getSessionId()) {
81
        $data[] = [
82
            get_lang('SessionName'),
83
            api_get_session_entity($trackExe->getSessionId())->getName(),
84
        ];
85
    }
86
87
    $data[] = [
88
        get_lang('CourseTitle'),
89
        api_get_course_entity($trackExe->getCId())->getTitle(),
90
    ];
91
    $data[] = [
92
        get_lang('ExerciseName'),
93
        $exercise->getUnformattedTitle(),
94
    ];
95
    $data[] = [
96
        $plugin->get_lang('ExerciseStartDateAndTime'),
97
        api_get_local_time($result['exe']->getStartDate(), null, null, true, true, true),
98
    ];
99
    $data[] = [
100
        $plugin->get_lang('ExerciseEndDateAndTime'),
101
        api_get_local_time($result['exe']->getExeDate(), null, null, true, true, true),
102
    ];
103
    $data[] = [
104
        get_lang('IP'),
105
        $result['exe']->getUserIp(),
106
    ];
107
    $data[] = [
108
        $plugin->get_lang('Motive'),
109
        $plugin->calculateMotive($outfocusedLimitCount, $timeLimitCount),
110
    ];
111
    $data[] = [];
112
113
    $data[] = [
114
        $plugin->get_lang('LevelReached'),
115
        get_lang('DateExo'),
116
        get_lang('Score'),
117
        $plugin->get_lang('Outfocused'),
118
        $plugin->get_lang('Returns'),
119
        $monitoringPluginIsEnabled ? $monitoringPlugin->get_lang('Snapshots') : '',
120
    ];
121
122
    if (ONE_PER_PAGE === $quizType) {
123
        $questionList = explode(',', $trackExe->getDataTracking());
124
125
        foreach ($questionList as $idx => $questionId) {
126
            $attempt = $attempsRepository->findOneBy(
127
                ['exeId' => $trackExe->getExeId(), 'questionId' => $questionId],
128
                ['tms' => 'DESC']
129
            );
130
131
            if (!$attempt) {
132
                continue;
133
            }
134
135
            $result = $exercise->manage_answer(
136
                $trackExe->getExeId(),
137
                $questionId,
138
                null,
139
                'exercise_result',
140
                false,
141
                false,
142
                true,
143
                false,
144
                $exercise->selectPropagateNeg()
145
            );
146
147
            $row = [
148
                get_lang('QuestionNumber').' '.($idx + 1),
149
                api_get_local_time($attempt->getTms()),
150
                $result['score'].' / '.$result['weight'],
151
                $focusedLogRepository->countByActionAndLevel($trackExe, FocusedLog::TYPE_OUTFOCUSED, $questionId),
152
                $focusedLogRepository->countByActionAndLevel($trackExe, FocusedLog::TYPE_RETURN, $questionId),
153
                getSnapshotListForLevel($questionId, $trackExe),
154
            ];
155
156
            $data[] = $row;
157
        }
158
    } elseif (ALL_ON_ONE_PAGE === $quizType) {
159
    }
160
161
    $data[] = [];
162
    $data[] = [];
163
    $data[] = [];
164
}
165
166
Export::arrayToXls($data);
167
168
function getSessionIdFromFormValues(array $formValues, array $fieldVariableList): array
169
{
170
    $fieldItemIdList = [];
171
    $objFieldValue = new ExtraFieldValue('session');
172
173
    foreach ($fieldVariableList as $fieldVariable) {
174
        if (!isset($formValues["extra_$fieldVariable"])) {
175
            continue;
176
        }
177
178
        $itemValues = $objFieldValue->get_item_id_from_field_variable_and_field_value(
179
            $fieldVariable,
180
            $formValues["extra_$fieldVariable"],
181
            false,
182
            false,
183
            true
184
        );
185
186
        foreach ($itemValues as $itemValue) {
187
            $fieldItemIdList[] = (int) $itemValue['item_id'];
188
        }
189
    }
190
191
    return array_unique($fieldItemIdList);
192
}
193
194
function findResults(array $formValues, EntityManagerInterface $em, ExerciseFocusedPlugin $plugin)
195
{
196
    $cId = api_get_course_int_id();
197
198
    $qb = $em->createQueryBuilder();
199
    $qb
200
        ->select('te AS exe, q.title, te.startDate , u.firstname, u.lastname, u.username')
201
        ->from(TrackEExercises::class, 'te')
202
        ->innerJoin(CQuiz::class, 'q', Join::WITH, 'te.exeExoId = q.iid')
203
        ->innerJoin(User::class, 'u', Join::WITH, 'te.exeUserId = u.id');
204
205
    $params = [];
206
207
    if ($cId) {
208
        $qb->andWhere($qb->expr()->eq('te.cId', ':cId'));
209
210
        $params['cId'] = $cId;
211
    }
212
213
    $sessionItemIdList = getSessionIdFromFormValues(
214
        $formValues,
215
        $plugin->getSessionFieldList()
216
    );
217
218
    if ($sessionItemIdList) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $sessionItemIdList of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
219
        $qb->andWhere($qb->expr()->in('te.sessionId', ':sessionItemIdList'));
220
221
        $params['sessionItemIdList'] = $sessionItemIdList;
222
    }
223
224
    if (!empty($formValues['username'])) {
225
        $qb->andWhere($qb->expr()->eq('u.username', ':username'));
226
227
        $params['username'] = $formValues['username'];
228
    }
229
230
    if (!empty($formValues['firstname'])) {
231
        $qb->andWhere($qb->expr()->eq('u.firstname', ':firstname'));
232
233
        $params['firstname'] = $formValues['firstname'];
234
    }
235
236
    if (!empty($formValues['lastname'])) {
237
        $qb->andWhere($qb->expr()->eq('u.lastname', ':lastname'));
238
239
        $params['lastname'] = $formValues['lastname'];
240
    }
241
242
    if (!empty($formValues['start_date'])) {
243
        $qb->andWhere(
244
            $qb->expr()->andX(
245
                $qb->expr()->gte('te.startDate', ':start_date'),
246
                $qb->expr()->lte('te.exeDate', ':end_date')
247
            )
248
        );
249
250
        $params['start_date'] = api_get_utc_datetime($formValues['start_date'].' 00:00:00', false, true);
251
        $params['end_date'] = api_get_utc_datetime($formValues['start_date'].' 23:59:59', false, true);
252
    }
253
254
    if (empty($params)) {
255
        return [];
256
    }
257
258
    if ($cId && !empty($formValues['id'])) {
259
        $qb->andWhere($qb->expr()->eq('q.iid', ':q_id'));
260
261
        $params['q_id'] = $formValues['id'];
262
    }
263
264
    $qb->setParameters($params);
265
266
    $query = $qb->getQuery();
267
268
    return $query->getResult();
269
}
270
271
function getSnapshotListForLevel(int $level, TrackEExercises $trackExe): string
272
{
273
    $monitoringPluginIsEnabled = ExerciseMonitoringPlugin::create()->isEnabled(true);
274
275
    if (!$monitoringPluginIsEnabled) {
276
        return '';
277
    }
278
279
    $user = api_get_user_entity($trackExe->getExeUserId());
280
    $monitoringLogRepository = Database::getManager()->getRepository(MonitoringLog::class);
281
282
    $monitoringLogsByQuestion = $monitoringLogRepository->findByLevelAndExe($level, $trackExe);
283
    $snapshotList = [];
284
285
    /** @var MonitoringLog $logByQuestion */
286
    foreach ($monitoringLogsByQuestion as $logByQuestion) {
287
        $snapshotUrl = ExerciseMonitoringPlugin::generateSnapshotUrl(
288
            $user->getId(),
289
            $logByQuestion->getImageFilename()
290
        );
291
        $snapshotList[] = api_get_local_time($logByQuestion->getCreatedAt()).' '.$snapshotUrl;
292
    }
293
294
    return implode(PHP_EOL, $snapshotList);
295
}
296