Proyectos de Subversion LeadersLinked - Antes de SPA

Rev

Rev 16 | Rev 41 | Ir a la última revisión | | Comparar con el anterior | Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 www 1
<?php
2
declare(strict_types=1);
3
 
4
namespace LeadersLinked\Controller;
5
 
6
 
7
use Laminas\Authentication\AuthenticationService;
8
use Laminas\Authentication\Result as AuthResult;
9
use Laminas\Db\Adapter\AdapterInterface;
10
use Laminas\Cache\Storage\Adapter\AbstractAdapter;
11
use Laminas\Mvc\Controller\AbstractActionController;
12
use Laminas\Log\LoggerInterface;
13
use Laminas\View\Model\JsonModel;
14
 
15
use LeadersLinked\Authentication\AuthAdapter;
16
use LeadersLinked\Mapper\UserMapper;
17
use LeadersLinked\Mapper\EmailTemplateMapper;
18
use LeadersLinked\Model\User;
19
use LeadersLinked\Model\UserType;
20
 
21
use LeadersLinked\Library\QueueEmail;
22
use LeadersLinked\Library\Functions;
23
use LeadersLinked\Model\EmailTemplate;
24
use LeadersLinked\Mapper\UserPasswordMapper;
25
use LeadersLinked\Mapper\DeviceMapper;
26
use LeadersLinked\Model\Device;
27
use LeadersLinked\Mapper\ApplicationMapper;
28
use LeadersLinked\Model\Application;
29
use LeadersLinked\Validator\PasswordStrengthCheck;
30
 
31
use LeadersLinked\Mapper\CompanyMapper;
32
use LeadersLinked\Model\Company;
33
use LeadersLinked\Mapper\CompanyMicrolearningTopicMapper;
34
use LeadersLinked\Mapper\CompanyMicrolearningCapsuleMapper;
35
use LeadersLinked\Mapper\CompanyMicrolearningSlideMapper;
36
use LeadersLinked\Model\CompanyMicrolearningSlide;
37
use LeadersLinked\Mapper\CompanyMicrolearningUserLogMapper;
38
use LeadersLinked\Mapper\CompanyMicrolearningUserProgressMapper;
39
use LeadersLinked\Mapper\CompanyMicrolearningQuizMapper;
40
use LeadersLinked\Mapper\CompanyMicrolearningQuestionMapper;
41
use LeadersLinked\Mapper\CompanyMicrolearningAnswerMapper;
42
use LeadersLinked\Model\CompanyMicrolearningUserProgress;
43
use LeadersLinked\Model\CompanyMicrolearningUserLog;
44
use LeadersLinked\Mapper\DeviceHistoryMapper;
45
use LeadersLinked\Model\DeviceHistory;
46
use LeadersLinked\Mapper\PushMapper;
47
use LeadersLinked\Model\Push;
48
use LeadersLinked\Mapper\CompanyMicrolearningCapsuleUserMapper;
49
use LeadersLinked\Mapper\CompanyServiceMapper;
50
use LeadersLinked\Model\Service;
51
use LeadersLinked\Model\CompanyService;
52
use LeadersLinked\Model\CompanyMicrolearningCapsuleUser;
53
use LeadersLinked\Model\CompanyMicrolearningUserQuiz;
54
use LeadersLinked\Mapper\CompanyMicrolearningUserQuizMapper;
55
use LeadersLinked\Mapper\CompanyMicrolearningUserMapper;
56
use LeadersLinked\Model\CompanyMicrolearningUser;
57
use LeadersLinked\Mapper\PushTemplateMapper;
58
use LeadersLinked\Model\PushTemplate;
59
 
60
 
61
class ServiceController extends AbstractActionController
62
{
63
 
64
 
65
    /**
66
     *
67
     * @var AdapterInterface
68
     */
69
    private $adapter;
70
 
71
 
72
    /**
73
     *
74
     * @var AbstractAdapter
75
     */
76
    private $cache;
77
 
78
    /**
79
     *
80
     * @var  LoggerInterface
81
     */
82
    private $logger;
83
 
84
    /**
85
     *
86
     * @var array
87
     */
88
    private $config;
89
 
90
    /**
91
     *
92
     * @param AdapterInterface $adapter
93
     * @param AbstractAdapter $cache
94
     * @param LoggerInterface $logger
95
     * @param array $config
96
     */
97
    public function __construct($adapter, $cache , $logger, $config)
98
    {
99
        $this->adapter      = $adapter;
100
        $this->cache        = $cache;
101
        $this->logger       = $logger;
102
        $this->config       = $config;
103
    }
104
 
105
    public function signoutAction()
106
    {
107
        $currentUser = $this->plugin('currentUserPlugin');
108
        if($currentUser->hasIdentity()) {
109
            $device_uuid = $currentUser->getDeviceId();
110
            if($device_uuid) {
111
                $deviceMapper = DeviceMapper::getInstance($this->adapter);
112
                $device = $deviceMapper->fetchOne($device_uuid);
113
                if($device) {
114
                    $deviceMapper->signout($device);
115
                }
116
            }
117
 
118
 
119
            $this->logger->info('Desconexión del mobile', ['user_id' => $currentUser->getUserId(), 'ip' => Functions::getUserIP()]);
120
        }
121
        $authService = new \Laminas\Authentication\AuthenticationService();
122
        $authService->clearIdentity();
123
 
124
        return new JsonModel([
125
            'success' => true,
126
            'data' => 'LABEL_SIGNOUT_SUCCESSFULL'
127
        ]);
128
    }
129
 
130
    public function fcmAction()
131
    {
132
        $request = $this->getRequest();
133
 
134
        if($request->isPost()) {
135
 
136
            $rawdata = file_get_contents("php://input");
137
            error_log('$rawdata = ' . $rawdata );
138
 
139
            $device_uuid      = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
140
            $token          = filter_var($this->params()->fromPost('token', ''), FILTER_SANITIZE_STRING);
141
            $sync_id        = filter_var($this->params()->fromPost('sync_id', ''), FILTER_SANITIZE_NUMBER_INT);
142
 
143
            /*
144
            echo '$device_uuid = ' . $device_uuid .PHP_EOL;
145
            echo '$token = ' . $token .PHP_EOL;
146
            echo '$sync_id  = ' . $sync_id  .PHP_EOL;
147
            */
148
            $ok = $device_uuid && strlen($device_uuid) == 36 && $sync_id;
149
            $ok = $ok && strlen($token) <= 512;
150
 
151
 
152
            if(!$ok) {
153
                return new JsonModel([
154
                    'success' => false,
155
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
156
                ]);
157
            }
158
 
159
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
160
            $device = $deviceMapper->fetchOne($device_uuid);
161
            if(!$device) {
162
                return new JsonModel([
163
                    'success' => false,
164
                    'data' => 'ERROR_DEVICE_NOT_FOUND',
165
                ]);
166
            }
167
 
168
 
169
            $applicationMapper = ApplicationMapper::getInstance($this->adapter);
170
            $application = $applicationMapper->fetchOne($device->application_id);
171
            if(!$application) {
172
                return new JsonModel([
173
                    'success' => false,
174
                    'data' => 'ERROR_APPLICATION_NOT_FOUND',
175
                ]);
176
            }
177
 
178
            if($application->status == Application::STATUS_INACTIVE) {
179
                return new JsonModel([
180
                    'success' => false,
181
                    'data' => 'ERROR_APPLICATION_IS_INACTIVE',
182
                ]);
183
            }
184
 
185
            $device->token = $token;
186
            $device->ip = Functions::getUserIP();
187
            $result = $deviceMapper->update($device);
188
 
189
 
190
            if($result) {
191
                return new JsonModel([
192
                    'success' => true,
193
                    'data' => [
194
                        'sync_id' => $sync_id
195
                    ]
196
                ]);
197
            } else {
198
                return new JsonModel([
199
                    'success' => false,
200
                    'data' => 'ERROR_THERE_WAS_AN_ERROR',
201
                ]);
202
            }
203
 
204
        }
205
 
206
        return new JsonModel([
207
            'success' => false,
208
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
209
        ]);
210
    }
211
 
212
    public function checkSessionAction()
213
    {
214
        $request = $this->getRequest();
215
 
216
        if($request->isPost()) {
217
            $device_uuid  = trim(filter_var($this->params()->fromPost('device_id', ''), FILTER_SANITIZE_STRING));
218
            $secret     = trim(filter_var($this->params()->fromPost('secret', ''), FILTER_SANITIZE_STRING));
219
            $rand       = filter_var($this->params()->fromPost('rand', ''), FILTER_SANITIZE_NUMBER_INT);
220
            $created    = trim(filter_var($this->params()->fromPost('created', ''), FILTER_SANITIZE_STRING));
221
 
222
            if(!$device_uuid || !$secret || !$rand || !$created) {
223
                return new JsonModel([
224
                    'success' => false,
225
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID'
226
                ]);
227
            }
228
 
229
            $dt = \DateTime::createFromFormat('Y-m-d\TH:i:s',  $created);
230
            if(!$dt) {
231
                return new JsonModel([
232
                    'success' => false,
233
                    'data' => 'ERROR_PARAMETERS_ARE_INCORRECTLY_FORMATTED'
234
                ]);
235
            }
236
 
237
 
238
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
239
            $device = $deviceMapper->fetchOne($device_uuid);
240
            if(!$device) {
241
                return new JsonModel([
242
                    'success' => false,
243
                    'data' => 'ERROR_DEVICE_NOT_FOUND'
244
                ]);
245
            }
246
 
247
 
248
            $passworVerification = md5($device->password . ':' . $created . ':'  . $rand);
249
            if($secret != $passworVerification) {
250
                return new JsonModel([
251
                    'success' => false,
252
                    'data' => 'ERROR_WEBSERVICE_PASSWORD'
253
                ]);
254
            }
255
 
256
 
257
            $userMapper = UserMapper::getInstance($this->adapter);
258
            $user = $userMapper->fetchOne($device->user_id);
259
 
260
            if(User::BLOCKED_YES == $user->blocked) {
261
                return new JsonModel([
262
                    'success' => false,
263
                    'data' => 'ERROR_USER_IS_BLOCKED'
264
                ]);
265
            }
266
 
267
            if(User::STATUS_INACTIVE == $user->status) {
268
                return new JsonModel([
269
                    'success' => false,
270
                    'data' =>'ERROR_USER_IS_INACTIVE'
271
                ]);
272
            }
273
 
274
 
275
            return new JsonModel([
276
                'success' => true,
277
                'data' => [
278
                    'user_uuid' => $device->user_uuid
279
                ]
280
            ]);
281
 
282
        }
283
 
284
        return new JsonModel([
285
            'success' => false,
286
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
287
        ]);
288
    }
289
 
290
    public function deviceAction()
291
    {
292
 
293
        $rawdata = file_get_contents("php://input");
294
        error_log('$rawdata = ' . $rawdata );
295
 
296
        $request = $this->getRequest();
297
 
298
        if($request->isPost()) {
299
            //print_r($_POST);
300
 
301
 
302
            $application_id = filter_var($this->params()->fromPost('application_id', 0), FILTER_SANITIZE_NUMBER_INT);
303
            $device_uuid    = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
304
            $manufacturer   = filter_var($this->params()->fromPost('manufacturer', ''), FILTER_SANITIZE_STRING);
305
            $platform       = filter_var($this->params()->fromPost('platform', ''), FILTER_SANITIZE_STRING);
306
            $brand          = filter_var($this->params()->fromPost('brand', ''), FILTER_SANITIZE_STRING);
307
            $version        = filter_var($this->params()->fromPost('version', ''), FILTER_SANITIZE_STRING);
308
            $model          = filter_var($this->params()->fromPost('model', ''), FILTER_SANITIZE_STRING);
309
            $sync_id        = filter_var($this->params()->fromPost('sync_id', ''), FILTER_SANITIZE_NUMBER_INT);
310
 
311
            $ok = $application_id && $device_uuid && strlen($device_uuid) == 36 && $sync_id;
312
            $ok = $ok && strlen($manufacturer) <= 250;
313
            $ok = $ok && strlen($brand) <= 250;
314
            $ok = $ok && strlen($version) <= 250;
315
            $ok = $ok && strlen($model) <= 250;
316
 
317
            if(!$ok) {
318
                return new JsonModel([
319
                    'success' => false,
320
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
321
                ]);
322
            }
323
 
324
 
325
            $applicationMapper = ApplicationMapper::getInstance($this->adapter);
326
            $application = $applicationMapper->fetchOne($application_id);
327
            if(!$application) {
328
                return new JsonModel([
329
                    'success' => false,
330
                    'data' => 'ERROR_APPLICATION_NOT_FOUND',
331
                ]);
332
            }
333
 
334
            if($application->status == Application::STATUS_INACTIVE) {
335
                return new JsonModel([
336
                    'success' => false,
337
                    'data' => 'ERROR_APPLICATION_IS_INACTIVE',
338
                ]);
339
            }
340
 
341
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
342
            $device = $deviceMapper->fetchOne($device_uuid);
343
 
344
 
345
 
346
 
347
            if($device) {
348
                $device->platform       = $platform;
349
                $device->manufacturer   = $manufacturer;
350
                $device->brand          = $brand;
351
                $device->version        = $version;
352
                $device->model          = $model;
353
                $device->ip             = Functions::getUserIP();
354
                $result                 = $deviceMapper->update($device);
355
 
356
            } else {
357
                $device                 = new Device();
358
                $device->id             = $device_uuid;
359
                $device->application_id = $application->id;
360
                $device->manufacturer   = $manufacturer;
361
                $device->brand          = $brand;
362
                $device->version        = $version;
363
                $device->model          = $model;
364
                $device->platform       = $platform;
365
                $device->ip             = Functions::getUserIP();
366
                $device->aes            = Functions::generatePassword(16);
367
                $device->password       = Functions::generatePassword(32);
368
                $result                 = $deviceMapper->insert($device);
369
            }
370
 
371
 
372
 
373
            if($result) {
374
                return new JsonModel([
375
                    'success' => true,
376
                    'data' => [
377
                        'sync_id'   => $sync_id,
378
                        'aes'       => $device->aes,
379
                        'password'  => $device->password,
380
                    ]
381
                ]);
382
            } else {
383
                return new JsonModel([
384
                    'success' => false,
385
                    'data' => 'ERROR_THERE_WAS_AN_ERROR',
386
                ]);
387
            }
388
 
389
        }
390
 
391
        return new JsonModel([
392
            'success' => false,
393
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
394
        ]);
395
 
396
    }
397
 
398
    public function microlearningCheckChangesAction()
399
    {
400
        $request = $this->getRequest();
401
 
402
        if($request->isPost()) {
403
            $currentUserPlugin = $this->plugin('currentUserPlugin');
404
            $user = $currentUserPlugin->getUser();
405
 
406
            $rawdata = file_get_contents("php://input");
407
            error_log('$rawdata = ' . $rawdata );
408
 
409
 
410
            $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
411
 
412
 
413
            $device_uuid        = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
414
            $max_date_changes   = filter_var($this->params()->fromPost('max_date_changes', ''), FILTER_SANITIZE_STRING);
415
            $max_ids            = filter_var($this->params()->fromPost('max_ids', ''), FILTER_SANITIZE_NUMBER_INT);
416
 
417
 
418
            $ids = [];
419
            for($i = 1; $i <= $max_ids; $i++)
420
            {
421
                $id = filter_var($this->params()->fromPost('id_' . $i, ''), FILTER_SANITIZE_STRING);
422
                if(empty($id)) {
423
                    continue;
424
                }
425
 
426
                $pattern = '/[A-Za-z0-9\-]+\|[A-Za-z0-9\-]+/';
427
                $matches = [];  preg_match($pattern, $id, $matches, PREG_OFFSET_CAPTURE);
428
                if(count($matches) > 1) {
429
                    array_push($ids, $matches[0]);
430
                }
431
 
432
            }
433
 
434
 
435
 
436
            if($max_date_changes) {
437
                $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $max_date_changes);
438
                if($dt) {
439
                  $max_date_changes = $dt->format('Y-m-d H:i:s');
440
                } else {
441
                    $max_date_changes = '';
442
                }
443
            } else {
444
                $max_date_changes = '';
445
            }
446
 
447
 
448
            error_log('device_uuid = ' . $device_uuid . ' max_date_changes = ' . $max_date_changes);
449
 
450
            $ok = $device_uuid && strlen($device_uuid);
451
 
452
            if(!$ok) {
453
                return new JsonModel([
454
                    'success' => false,
455
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
456
                ]);
457
            }
458
 
459
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
460
            $device = $deviceMapper->fetchOne($device_uuid);
461
 
462
 
463
            if(!$device) {
464
                return new JsonModel([
465
                    'success' => false,
466
                    'data' => 'ERROR_DEVICE_NOT_FOUND'
467
                ]);
468
            } else {
469
                $device->ip = Functions::getUserIP();
470
                $deviceMapper->update($device);
471
            }
472
 
473
            //Cargamos la fecha máxima del cambio
474
            $companyMicrolearningUserMapper = CompanyMicrolearningUserMapper::getInstance($this->adapter);
475
            $max_date_changes_db = $companyMicrolearningUserMapper->fetchMaxDateChanges($user->id);
476
 
477
            //Si la fecha es vacia agregamos la fecha máxima de la asignación de la capsula
478
            if(!$max_date_changes_db) {
479
                $companyUsers = [];
480
                $companyMicrolearningCapsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
481
                $capsules = $companyMicrolearningCapsuleUserMapper->fetchAllActiveByUserId($user->id);
482
                foreach($capsules as $capsule)
483
                {
484
 
485
 
486
 
487
                    if(empty($companyUsers[$capsule->company_id])) {
488
                        $companyUsers[$capsule->company_id] = $capsule->updated_on;
489
                    } else {
490
 
491
                        if($capsule->updated_on > $companyUsers[$capsule->company_id]) {
492
                            $companyUsers[$capsule->company_id] = $capsule->updated_on;
493
                        }
494
 
495
                    }
496
 
497
                }
498
 
499
                $max_date_changes_db = '';
500
                foreach($companyUsers as $company_id => $update_on)
501
                {
502
 
503
                    $max_date_changes_db = $max_date_changes_db < $update_on ? $update_on : $max_date_changes_db;
504
 
505
                    $companyMicrolearningUser = new CompanyMicrolearningUser();
506
                    $companyMicrolearningUser->company_id = $company_id;
507
                    $companyMicrolearningUser->user_id = $user->id;
508
                    $companyMicrolearningUser->added_on = $update_on;
509
                    $companyMicrolearningUser->updated_on = $update_on;
510
 
511
                    $companyMicrolearningUserMapper->insert($companyMicrolearningUser);
512
                }
513
            }
514
 
515
 
516
            error_log("max_date_changes = $max_date_changes, max_date_changes_db = $max_date_changes_db");
517
 
518
            //Si la que tiene el dispositivo es diferente a la fecha máxima almacenada
519
            $newCapsules = 0;
520
            if($max_date_changes != $max_date_changes_db) {
521
                if(is_array($ids)) {
522
                    $companyMicrolearningTopicMapper = CompanyMicrolearningTopicMapper::getInstance($this->adapter);
523
                    $companyMicrolearningTopics = $companyMicrolearningTopicMapper->fetchAllActive();
524
 
525
                    $topics = [];
526
                    foreach($companyMicrolearningTopics as $topic)
527
                    {
528
                        $topics[$topic->id] = $topic->uuid;
529
                    }
530
 
531
                    $companyMicrolearningCapsuleMapper = CompanyMicrolearningCapsuleMapper::getInstance($this->adapter);
532
                    $companyMicrolearningCapsules = $companyMicrolearningCapsuleMapper->fetchAllActiveAndPublic();
533
 
534
                    $capsules = [];
535
                    foreach($companyMicrolearningCapsules as $capsule)
536
                    {
537
                        $capsules[$capsule->id] = $capsule->uuid;
538
                    }
539
 
540
                    $companyMicrolearningCapsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
541
                    $user_capsules = $companyMicrolearningCapsuleUserMapper->fetchAllActiveByUserId($user->id);
542
 
543
                    foreach($user_capsules as $user_capsule)
544
                    {
545
                        $topic_uuid     = isset($topics[$user_capsule->topic_id]) ? $topics[$user_capsule->topic_id] : '';
546
                        $capsule_uuid   = isset($capsules[$user_capsule->capsule_id]) ?  $capsules[$user_capsule->capsule_id] : '';
547
 
548
                        if(!$topic_uuid || !$capsule_uuid) {
549
                            continue;
550
                        }
551
 
552
                        $key = $topic_uuid . '|' . $capsule_uuid;
553
                        if(!in_array($key, $ids)) {
554
                            $newCapsules++;
555
                        }
556
                    }
557
                }
558
            }
559
 
560
 
561
            //echo 'Vamos a lanzar un PUSH' . PHP_EOL;
562
            if($newCapsules) {
563
 
564
                if($device->token)
565
                {
566
 
567
                    $pushMapper = PushMapper::getInstance($this->adapter);
568
                    $pushTemplateMapper = PushTemplateMapper::getInstance($this->adapter);
569
                    $pushTemplate = $pushTemplateMapper->fetchOne(PushTemplate::ID_MICRO_LEARNING_NEW_CONTENT);
570
 
571
                    //echo 'PushTemplate' . PHP_EOL;
572
                    //print_r($pushTemplate);
573
 
574
                    $applicationMapper = ApplicationMapper::getInstance($this->adapter);
575
                    $application = $applicationMapper->fetchOne(Application::TWOGETSKILLS);
576
 
577
 
578
                    //echo 'Application';
579
                    //print_r($application);
580
                    if($pushTemplate && $application) {
581
                         $push = new Push();
582
                        $push->status = Push::STATUS_PENDING;
583
                        $push->data = json_encode([
584
                            'server' => [
585
                                'key' =>   $application->key,
586
                            ],
587
                            'push' => [
588
                                'registration_ids'   => [
589
                                    $device->token,
590
                                ],
591
                                'notification' => [
592
                                    'body' =>  $pushTemplate->body,
593
                                    'title' => $pushTemplate->title,
594
                                    'vibrate' => 1,
595
                                    'sound' =>  1,
596
 
597
 
598
                                ],
599
                                'data' => [
600
                                    'new_capsules' => $newCapsules,
601
                                ]
602
                            ]
603
                        ]);
604
                        $pushMapper->insert($push);
605
                    }
606
                }
607
 
608
                $dataSync = $this->getSyncData($user,false, false);
609
            } else {
610
                $dataSync = [];
611
            }
612
 
613
 
614
 
615
            //error_log('$max_date_changes_db = ' . $max_date_changes_db);
616
 
617
            $dt = \DateTime::createFromFormat('Y-m-d H:i:s', $max_date_changes_db);
618
            if($dt) {
619
                $max_date_changes_db = $dt->format($serviceDatetimeFormat);
620
            } else {
621
                $max_date_changes_db = '';
622
            }
623
 
624
            $data = [
625
                'success'   => true,
626
                'data'      =>[
627
                    'user' => [
628
                        'uuid' => $user->uuid,
629
                        'first_name' => $user->first_name,
630
                        'last_name' => $user->last_name,
631
                        'email' => $user->email,
632
                        'image' => $this->url()->fromRoute('services/storage',['type' => 'user', 'code' => $user->uuid, 'filename' => $user->image], ['force_canonical' => true]),
633
                    ],
634
                    'max_date_changes' => $max_date_changes_db,
635
                    'topics'    => isset( $dataSync['topics'] ) ? $dataSync['topics'] : [],
636
                    'quizzes'   => isset( $dataSync['quizzes'] ) ? $dataSync['quizzes'] : [],
637
 
638
                ]
639
            ];
640
 
641
            //error_log(print_r($data, true));
642
 
643
            return new JsonModel($data);
644
        }
645
 
646
        return new JsonModel([
647
            'success' => false,
648
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
649
        ]);
650
 
651
    }
652
 
653
 
654
 
655
    public function microlearningRefreshAction()
656
    {
657
        $request = $this->getRequest();
658
 
659
        if($request->isGet()) {
660
            $currentUserPlugin = $this->plugin('currentUserPlugin');
661
            $user = $currentUserPlugin->getUser();
662
 
663
            $dataSync = $this->getSyncData($user,false, false);
664
 
665
            //Cargamos la fecha máxima del cambio
666
            $companyMicrolearningUserMapper = CompanyMicrolearningUserMapper::getInstance($this->adapter);
667
            $max_date_changes_db = $companyMicrolearningUserMapper->fetchMaxDateChanges($user->id);
668
 
669
            //Si la fecha es vacia agregamos la fecha máxima de la asignación de la capsula
670
            if(!$max_date_changes_db) {
671
                $companyUsers = [];
672
                $companyMicrolearningCapsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
673
                $capsules = $companyMicrolearningCapsuleUserMapper->fetchAllActiveByUserId($user->id);
674
                foreach($capsules as $capsule)
675
                {
676
 
677
 
678
 
679
                    if(empty($companyUsers[$capsule->company_id])) {
680
                        $companyUsers[$capsule->company_id] = $capsule->updated_on;
681
                    } else {
682
 
683
                        if($capsule->updated_on > $companyUsers[$capsule->company_id]) {
684
                            $companyUsers[$capsule->company_id] = $capsule->updated_on;
685
                        }
686
 
687
                    }
688
 
689
                }
690
 
691
                $max_date_changes_db = '';
692
                foreach($companyUsers as $company_id => $update_on)
693
                {
694
 
695
                    $max_date_changes_db = $max_date_changes_db < $update_on ? $update_on : $max_date_changes_db;
696
 
697
                    $companyMicrolearningUser = new CompanyMicrolearningUser();
698
                    $companyMicrolearningUser->company_id = $company_id;
699
                    $companyMicrolearningUser->user_id = $user->id;
700
                    $companyMicrolearningUser->added_on = $update_on;
701
                    $companyMicrolearningUser->updated_on = $update_on;
702
 
703
                    $companyMicrolearningUserMapper->insert($companyMicrolearningUser);
704
                }
705
            }
706
 
707
            $dt = \DateTime::createFromFormat('Y-m-d H:i:s', $max_date_changes_db);
708
            if($dt) {
709
                $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
710
                $max_date_changes_db = $dt->format($serviceDatetimeFormat);
711
            } else {
712
                $max_date_changes_db = '';
713
            }
714
 
715
            return new JsonModel([
716
                'success'   => true,
717
                'data'      =>[
718
                    'user' => [
719
                        'uuid' => $user->uuid,
720
                        'first_name' => $user->first_name,
721
                        'last_name' => $user->last_name,
722
                        'email' => $user->email,
723
                        'image' => $this->url()->fromRoute('services/storage',['type' => 'user', 'code' => $user->uuid, 'filename' => $user->image], ['force_canonical' => true]),
724
                    ],
725
                    'max_date_changes' => $max_date_changes_db,
726
                    'topics'    => $dataSync['topics'],
727
                    'quizzes'   => $dataSync['quizzes'],
728
 
729
                ]
730
            ]);
731
        }
732
 
733
        return new JsonModel([
734
            'success' => false,
735
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
736
        ]);
737
    }
738
 
739
 
740
    public function signinAction()
741
    {
742
        $request = $this->getRequest();
743
 
744
        if($request->isPost()) {
745
 
746
 
747
            $rawdata = file_get_contents("php://input");
748
            error_log('$rawdata = ' . $rawdata );
749
 
750
 
751
            $application_id = filter_var($this->params()->fromPost('application_id', 0), FILTER_SANITIZE_NUMBER_INT);
752
            $device_uuid    = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
753
            $email          = filter_var($this->params()->fromPost('email', ''), FILTER_SANITIZE_EMAIL);
754
            $password       = filter_var($this->params()->fromPost('password', ''), FILTER_SANITIZE_STRING);
755
            //$encrypter      = filter_var($this->params()->fromPost('encrypter', ''), FILTER_SANITIZE_STRING);
756
 
757
 
758
 
759
            $ok = $application_id && $device_uuid && strlen($device_uuid) == 36;
760
            $ok = $ok && $email && $password;
761
            //$ok = $ok && in_array($encrypter, ['CryptoJsAes','RNCryptor','AesCipher']);
762
 
763
            if(!$ok) {
764
                return new JsonModel([
765
                    'success' => false,
766
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
767
                ]);
768
            }
769
 
770
 
771
            $applicationMapper = ApplicationMapper::getInstance($this->adapter);
772
            $application = $applicationMapper->fetchOne($application_id);
773
            if(!$application) {
774
                return new JsonModel([
775
                    'success' => false,
776
                    'data' => 'ERROR_APPLICATION_NOT_FOUND',
777
                ]);
778
            }
779
 
780
            if($application->status == Application::STATUS_INACTIVE) {
781
                return new JsonModel([
782
                    'success' => false,
783
                    'data' => 'ERROR_APPLICATION_IS_INACTIVE',
784
                ]);
785
            }
786
 
787
 
788
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
789
            $device = $deviceMapper->fetchOne($device_uuid);
790
            if(!$device) {
791
                $device                 = new Device();
792
                $device->id             = $device_uuid;
793
                $device->application_id = $application->id;
794
                $device->ip             = Functions::getUserIP();
795
                $device->aes            = Functions::generatePassword(16);
796
                $device->password       = Functions::generatePassword(32);
797
                $result                 = $deviceMapper->insert($device);
798
 
799
                if(!$result) {
800
                    return new JsonModel([
801
                        'success' => false,
802
                        'data' => 'ERROR_DEVICE_NOT_FOUND',
803
                    ]);
804
                }
805
            }
806
 
807
            /*
808
            if($encrypter == 'CryptoJsAes') {
809
 
810
 
811
                $email = html_entity_decode($email);
812
                $password = html_entity_decode($password);
813
 
814
 
815
                ob_start();
816
 
817
                $email      = CryptoJsAes::decrypt($email, $device->aes);
818
                $password   = CryptoJsAes::decrypt($password, $device->aes);
819
 
820
                ob_end_clean();
821
 
822
                if(!$email || !$password) {
823
                    return new JsonModel([
824
                        'success' => false,
825
                        'data' => 'ERROR_WEBSERVICE_PASSWORD_ENCRYPTION_FAILED',
826
                    ]);
827
                }
828
            } else if($encrypter == 'RNCryptor') {
829
                $cryptor = new \RNCryptor\RNCryptor\Decryptor;
830
                $email = $cryptor->decrypt($email, $device->aes);
831
                $password = $cryptor->decrypt($password, $device->aes);
832
 
833
                if(!$email || !$password) {
834
                    return new JsonModel([
835
                        'success' => false,
836
                        'data' => 'ERROR_WEBSERVICE_PASSWORD_ENCRYPTION_FAILED',
837
                    ]);
838
                }
839
 
840
 
841
            } else if($encrypter == 'AesCipher') {
842
 
843
                $emailDecrypted = AesCipher::decrypt($device->aes,$email);
844
                $passwordDecrypted = AesCipher::decrypt($device->aes,$password);
845
                if($emailDecrypted->hasError() || $passwordDecrypted->hasError()) {
846
                    return new JsonModel([
847
                        'success' => false,
848
                        'data' => 'ERROR_WEBSERVICE_PASSWORD_ENCRYPTION_FAILED',
849
                    ]);
850
                }
851
 
852
                $email = $emailDecrypted->getData();
853
                $password = $passwordDecrypted->getData();
854
            } else {
855
                return new JsonModel([
856
                    'success' => false,
857
                    'data' => 'ERROR_WEBSERVICE_PASSWORD_ENCRYPTION_FAILED',
858
                ]);
859
            }*/
860
 
861
 
862
            $authAdapter = new AuthAdapter($this->adapter);
863
            $authAdapter->setData($email, $password);
864
 
865
            $authService = new AuthenticationService();
866
            $result = $authService->authenticate($authAdapter);
867
 
868
            if($result->getCode() == AuthResult::SUCCESS) {
869
 
870
                $userMapper = UserMapper::getInstance($this->adapter);
871
                $user = $userMapper->fetchOneByEmail($email);
872
 
873
 
874
                $device->user_id    = $user->id;
875
                $device->ip         = Functions::getUserIP();
876
                if($deviceMapper->update($device)) {
877
 
878
                    $ip = Functions::getUserIP();
879
 
880
                    $deviceHistoryMapper = DeviceHistoryMapper::getInstance($this->adapter);
881
                    $deviceHistory = $deviceHistoryMapper->fetchOneByDeviceIdAndUserIdAndIp($device->id, $user->id, $ip);
882
                    if($deviceHistory) {
883
                        $deviceHistoryMapper->update($deviceHistory);
884
                    } else {
885
                        $deviceHistory = new DeviceHistory();
886
                        $deviceHistory->device_id = $device->id;
887
                        $deviceHistory->user_id = $user->id;
888
                        $deviceHistory->ip = $ip;
889
                        $deviceHistoryMapper->insert($deviceHistory);
890
                    }
891
 
892
                    $pushMapper = PushMapper::getInstance($this->adapter);
893
 
894
                    $userDevices =  $deviceMapper->fetchAllByUserId($user->id);
895
                    foreach($userDevices as $userDevice)
896
                    {
897
 
898
 
899
                        if($userDevice->id != $device->id && $userDevice->token) {
900
 
901
                            $push = new Push();
902
                            $push->status = Push::STATUS_PENDING;
903
                            $push->data = json_encode([
904
                                'server' => [
905
                                    'key' =>   $application->key
906
                                 ],
907
                                 'push' => [
908
                                    'registration_ids'   => [
909
                                        $userDevice->token,
910
                                     ],
911
                                     /*'notification' => [
912
                                         'body' =>  'Se registro un inicio de sessión desde otro dispositivo',
913
                                         'title' => 'Inicio de sessión',
914
                                         'vibrate' => 1,
915
                                         'sound' =>  1
916
                                     ],*/
917
                                    'data' => [
918
                                        'command' => 'signout'
919
                                    ]
920
                                 ]
921
                             ]);
922
 
923
                            $pushMapper->insert($push);
924
 
925
                        }
926
                    }
927
 
928
 
929
                    $companyUsers = [];
930
                    $companyMicrolearningCapsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
931
                    $capsules = $companyMicrolearningCapsuleUserMapper->fetchAllActiveByUserId($user->id);
932
                    foreach($capsules as $capsule)
933
                    {
934
 
935
 
936
 
937
                        if(empty($companyUsers[$capsule->company_id])) {
938
                            $companyUsers[$capsule->company_id] = $capsule->updated_on;
939
                        } else {
940
 
941
                            if($capsule->updated_on > $companyUsers[$capsule->company_id]) {
942
                                $companyUsers[$capsule->company_id] = $capsule->updated_on;
943
                            }
944
 
945
                        }
946
 
947
                    }
948
 
949
                    $companyMicrolearningUserMapper = CompanyMicrolearningUserMapper::getInstance($this->adapter);
950
 
951
                    $maxDateChanges = $companyMicrolearningUserMapper->fetchMaxDateChanges($user->id);
952
                    if(!$maxDateChanges) {
953
 
954
 
955
                        $maxDateChanges = '';
956
                        foreach($companyUsers as $company_id => $update_on)
957
                        {
958
 
959
                            $maxDateChanges = $maxDateChanges < $update_on ? $update_on : $maxDateChanges;
960
 
961
                            $companyMicrolearningUser = new CompanyMicrolearningUser();
962
                            $companyMicrolearningUser->company_id = $company_id;
963
                            $companyMicrolearningUser->user_id = $user->id;
964
                            $companyMicrolearningUser->added_on = $update_on;
965
                            $companyMicrolearningUser->updated_on = $update_on;
966
 
967
                            $companyMicrolearningUserMapper->insert($companyMicrolearningUser);
968
                        }
969
 
970
 
971
                    }
972
 
973
 
974
 
975
                   $dt = \DateTime::createFromFormat('Y-m-d H:i:s', $maxDateChanges);
976
                   if($dt) {
977
                       $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
978
                       $maxDateChanges = $dt->format($serviceDatetimeFormat);
979
                   } else {
980
                       $maxDateChanges = '';
981
                   }
982
 
983
 
984
                    $data = [
985
                        'success'   => true,
986
                        'data'      =>[
987
                            'user' => [
988
                                'uuid' => $user->uuid,
989
                                'first_name' => $user->first_name,
990
                                'last_name' => $user->last_name,
991
                                'email' => $user->email,
992
                                'image' => $this->url()->fromRoute('services/storage',['type' => 'user', 'code' => $user->uuid, 'filename' => $user->image], ['force_canonical' => true]),
993
 
994
                             ],
995
                            'max_date_changes' => $maxDateChanges,
996
                            'device' => [
997
                                'aes' => $device->aes,
998
                                'password' => $device->password
999
                            ]
1000
 
1001
                        ]
1002
                    ];
1003
 
1004
                    if($application->id == Application::TWOGETSKILLS) {
1005
                        $dataSync = $this->getSyncData($user);
1006
 
1007
                        $data['data']['topics'] = $dataSync['topics'];
1008
                        $data['data']['quizzes'] = $dataSync['quizzes'];
1009
                        $data['data']['userlog'] = $dataSync['userlog'];
1010
                        $data['data']['progress'] = $dataSync['progress'];
1011
                    }
1012
 
1013
 
1014
 
1015
                    return new JsonModel($data);
1016
 
1017
 
1018
 
1019
                } else {
1020
                    return new JsonModel([
1021
                        'success' => false,
1022
                        'data' => 'ERROR_THERE_WAS_AN_ERROR',
1023
                    ]);
1024
                }
1025
 
1026
 
1027
            } else {
1028
                $message = $result->getMessages()[0];
1029
                if(!in_array($message, ['ERROR_USER_NOT_FOUND', 'ERROR_USER_PROVIDER_NOT_FOUND', 'ERROR_USER_EMAIL_HASNT_BEEN_VARIFIED', 'ERROR_USER_IS_BLOCKED',
1030
                    'ERROR_USER_IS_INACTIVE', 'ERROR_ENTERED_PASS_INCORRECT_USER_IS_BLOCKED', 'ERROR_ENTERED_PASS_INCORRECT_2',
1031
                    'ERROR_ENTERED_PASS_INCORRECT_1'])) {
1032
                }
1033
 
1034
                switch($message)
1035
                {
1036
                    case 'ERROR_USER_NOT_FOUND' :
1037
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - Email no existe', ['ip' => Functions::getUserIP()]);
1038
                        break;
1039
 
1040
                    case 'ERROR_USER_EMAIL_HASNT_BEEN_VARIFIED' :
1041
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - Email no verificado', ['ip' => Functions::getUserIP()]);
1042
                        break;
1043
 
1044
                    case 'ERROR_USER_IS_BLOCKED' :
1045
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - Usuario bloqueado', ['ip' => Functions::getUserIP()]);
1046
                        break;
1047
 
1048
                    case 'ERROR_USER_IS_INACTIVE' :
1049
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - Usuario inactivo', ['ip' => Functions::getUserIP()]);
1050
                        break;
1051
 
1052
 
1053
                    case 'ERROR_ENTERED_PASS_INCORRECT_USER_IS_BLOCKED':
1054
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - 3er Intento Usuario bloqueado', ['ip' => Functions::getUserIP()]);
1055
                        break;
1056
 
1057
 
1058
                    case 'ERROR_ENTERED_PASS_INCORRECT_2' :
1059
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - 1er Intento', ['ip' => Functions::getUserIP()]);
1060
                        break;
1061
 
1062
 
1063
                    case 'ERROR_ENTERED_PASS_INCORRECT_1' :
1064
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - 2do Intento', ['ip' => Functions::getUserIP()]);
1065
                        break;
1066
 
1067
 
1068
                    default :
1069
                        $message = 'ERROR_UNKNOWN';
1070
                        $this->logger->err('Error de ingreso a LeadersLinked de ' . $email . ' - Error desconocido', ['ip' => Functions::getUserIP()]);
1071
                        break;
1072
 
1073
 
1074
                }
1075
 
1076
 
1077
                return new JsonModel([
1078
                    'success'   => false,
1079
                    'data'   => $message
1080
                ]);
1081
            }
1082
 
1083
        }
1084
 
1085
        return new JsonModel([
1086
            'success' => false,
1087
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
1088
        ]);
1089
 
1090
    }
1091
 
1092
 
1093
 
1094
 
1095
    public function storageAction()
1096
    {
1097
 
1098
        // Get the file name from GET variable.
1099
        $code       = $this->params()->fromRoute('code', '');
1100
        $fileName   = $this->params()->fromRoute('filename', '');
1101
        $type       = $this->params()->fromRoute('type', 'user');
1102
 
1103
 
1104
        $no_image = $this->config['leaderslinked.images_default.no_image'];
1105
        $path = '';
1106
        switch($type)
1107
        {
1108
            case 'user' :
1109
                $no_image = $this->config['leaderslinked.images_default.user_image'];
1110
                $path = $this->config['leaderslinked.fullpath.user'];
1111
                break;
1112
 
1113
 
1114
            case 'user-profile' :
1115
                $no_image = $this->config['leaderslinked.images_default.user_profile'];
1116
                $path = $this->config['leaderslinked.fullpath.user'];
1117
                break;
1118
 
1119
            case 'user-cover' :
1120
                $no_image = $this->config['leaderslinked.images_default.user_cover'];
1121
                $path = $this->config['leaderslinked.fullpath.user'];
1122
                break;
1123
 
1124
            case 'company' :
1125
                $no_image = $this->config['leaderslinked.images_default.company_profile'];
1126
                $path = $this->config['leaderslinked.fullpath.company'];
1127
                break;
1128
 
1129
            case 'company-cover' :
1130
                $no_image = $this->config['leaderslinked.images_default.company_cover'];
1131
                $path = $this->config['leaderslinked.fullpath.company'];
1132
                break;
1133
 
1134
            case 'group' :
1135
                $no_image = $this->config['leaderslinked.images_default.group_profile'];
1136
                $path = $this->config['leaderslinked.fullpath.group'];
1137
                break;
1138
 
1139
            case 'group-cover' :
1140
                $no_image = $this->config['leaderslinked.images_default.group_cover'];
1141
                $path = $this->config['leaderslinked.fullpath.group'];
1142
                break;
1143
 
1144
            case 'job' :
1145
                $path = $this->config['leaderslinked.fullpath.job'];
1146
                break;
1147
 
1148
            case 'chat' :
1149
                $path = $this->config['leaderslinked.fullpath.chat'];
1150
                break;
1151
 
1152
            case 'feed' :
1153
                $path = $this->config['leaderslinked.fullpath.feed'];
1154
                break;
1155
 
1156
            case 'post' :
1157
                $path = $this->config['leaderslinked.fullpath.post'];
1158
                break;
1159
 
1160
            case 'microlearning-topic' :
1161
                $path = $this->config['leaderslinked.fullpath.microlearning_topic'];
1162
                break;
1163
 
1164
            case 'microlearning-capsule' :
1165
                $path = $this->config['leaderslinked.fullpath.microlearning_capsule'];
1166
                break;
1167
 
1168
            case 'microlearning-slide' :
1169
                $path = $this->config['leaderslinked.fullpath.microlearning_slide'];
1170
                break;
1171
 
1172
            default :
1173
                $path = $this->config['leaderslinked.fullpath.image'];
1174
                break;
1175
 
1176
        }
1177
        if($code && $fileName) {
1178
            $request_fullpath = $path . $code . DIRECTORY_SEPARATOR . $fileName;
1179
        } else {
1180
            $request_fullpath = $no_image;
1181
        }
1182
 
1183
        if(empty($fileName)) {
1184
            $extensions     = explode('.',$request_fullpath);
1185
            $extension      = strtolower(trim($extensions[count($extensions)-1]));
1186
            if ($extension=='jpg' || $extension=='jpeg' || $extension=='gif' || $extension == 'png') {
1187
                $request_fullpath =  $no_image;
1188
            }
1189
        }
1190
 
1191
 
1192
        if(file_exists($request_fullpath)) {
1193
 
1194
            // Try to open file
1195
            if (!is_readable($request_fullpath)) {
1196
                return $this->getResponse()->setStatusCode(500);
1197
            }
1198
 
1199
            // Get file size in bytes.
1200
            $fileSize = filesize($request_fullpath);
1201
 
1202
            // Get MIME type of the file.
1203
            $mimeType = mime_content_type($request_fullpath);
1204
            if($mimeType===false) {
1205
                $mimeType = 'application/octet-stream';
1206
            }
1207
 
1208
            $request_fullpath = trim($request_fullpath);
1209
            $length = strlen($request_fullpath);
1210
            if(substr($request_fullpath, $length - 1) == '/') {
1211
                $request_fullpath = substr($request_fullpath, 0, $length - 1);
1212
            }
1213
 
1214
 
1215
            $filename = basename($request_fullpath);
1216
 
1217
            header('Content-type: ' . $mimeType);
1218
            readfile($request_fullpath);
1219
 
1220
 
1221
            exit;
1222
            //header("X-Sendfile: $request_fullpath");
1223
            //header("Content-type: application/octet-stream");
1224
            //header('Content-Disposition: attachment; filename="' . basename($filename) . '"');
1225
 
1226
 
1227
            /*
1228
 
1229
 
1230
            if ($fd = fopen ($request_fullpath, "r")) {
1231
 
1232
                $fsize = filesize($request_fullpath);
1233
 
1234
                header("Content-type: $mimeType");
1235
                header("Accept-Ranges: bytes");
1236
 
1237
                //header("Content-Disposition: attachment; filename=\"$filename\"");
1238
 
1239
                header("Content-length: $fsize");
1240
                header("Cache-control: private");
1241
 
1242
                while(!feof($fd)) {
1243
                    $buffer = fread($fd, 2048);
1244
                    echo $buffer;
1245
                }
1246
            }
1247
 
1248
            fclose ($fd);
1249
            exit;*/
1250
 
1251
 
1252
            /*
1253
             $fileContent = file_get_contents($request_fullpath);
1254
            $response = $this->getResponse();
1255
            $headers = $response->getHeaders();
1256
            $headers->addHeaderLine('Accept-Ranges: bytes');
1257
            $headers->addHeaderLine('Content-type: ' . $mimeType);
1258
            $headers->addHeaderLine('Content-length: ' . $fileSize);
1259
 
1260
            /*
1261
            Date: Tue, 13 Jul 2021 03:11:42 GMT
1262
            Server: Apache/2.4.41 (Ubuntu)
1263
            Last-Modified: Mon, 28 Jun 2021 16:43:04 GMT
1264
            ETag: "54e4-5c5d62eed581e"
1265
            Accept-Ranges: bytes
1266
            Content-Length: 21732
1267
            Cache-Control: max-age=1
1268
            Expires: Tue, 13 Jul 2021 03:11:43 GMT
1269
            Keep-Alive: timeout=5, max=100
1270
            Connection: Keep-Alive
1271
            Content-Type: audio/mpeg
1272
            */
1273
 
1274
            /*
1275
            if($fileContent!==false) {
1276
                error_log($_SERVER['REQUEST_URI']);
1277
                error_log($request_fullpath);
1278
                return $response->setContent($fileContent);
1279
 
1280
                header('Content-Type: '.$mimeType );
1281
                readfile_chunked($filename);
1282
                exit;
1283
 
1284
            } else {
1285
                error_log('500');
1286
                $this->getResponse()->setStatusCode(500);
1287
                return;
1288
            }*/
1289
        } else {
1290
            error_log('404');
1291
            return $this->getResponse()->setStatusCode(404);
1292
        }
1293
 
1294
        return $this->getResponse();
1295
    }
1296
 
1297
 
1298
    public function syncAction()
1299
    {
1300
        $request = $this->getRequest();
1301
 
1302
        if($request->isPost()) {
1303
 
1304
            $rawdata = file_get_contents("php://input");
1305
            error_log('$rawdata = ' . $rawdata );
1306
 
1307
 
1308
            $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
1309
 
1310
            $device_uuid    = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
1311
            $sync_id        = filter_var($this->params()->fromPost('sync_id', ''), FILTER_SANITIZE_NUMBER_INT);
1312
            $data           = $this->params()->fromPost('data', '');
1313
 
1314
 
1315
 
1316
            error_log('device_uuid = ' . $device_uuid);
1317
            error_log('sync_id = ' . $sync_id);
1318
            error_log(print_r($data, true));
1319
 
1320
 
1321
            $ok = $device_uuid && strlen($device_uuid) == 36 && $data && $sync_id;
1322
 
1323
            if(!$ok) {
1324
                return new JsonModel([
1325
                    'success' => false,
1326
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
1327
                ]);
1328
            }
1329
 
1330
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
1331
            $device = $deviceMapper->fetchOne($device_uuid);
1332
 
1333
 
1334
            if(!$device) {
1335
                return new JsonModel([
1336
                    'success' => false,
1337
                    'data' => 'ERROR_DEVICE_NOT_FOUND'
1338
                ]);
1339
            } else {
1340
                $device->ip = Functions::getUserIP();
1341
                $deviceMapper->update($device);
1342
            }
1343
 
1344
 
1345
 
1346
            $data = json_decode($data, true);
1347
            $sync_type      = isset($data['sync_type']) ? filter_var($data['sync_type'], FILTER_SANITIZE_STRING) : '';
1348
            $user_uuid      = isset($data['user_uuid']) ? filter_var($data['user_uuid'], FILTER_SANITIZE_STRING) : '';
1349
            $company_uuid   = isset($data['company_uuid']) ? filter_var($data['company_uuid'], FILTER_SANITIZE_STRING) :  '';
1350
 
1351
    //
1352
 
1353
            if($user_uuid && $device->application_id = Application::TWOGETSKILLS  && $company_uuid && in_array($sync_type, ['microlearning-progress', 'microlearning-userlog', 'microlearning-quiz'])) {
1354
                $userMapper = UserMapper::getInstance($this->adapter);
1355
                $user = $userMapper->fetchOneByUuid($user_uuid);
1356
 
1357
                if(!$user) {
1358
                    return new JsonModel([
1359
                        'success' => false,
1360
                        'data' => [
1361
                            'sync_id' => $sync_id,
1362
                            'message' => 'ERROR_USER_NOT_FOUND',
1363
                            'fatal' => true
1364
                        ]
1365
                    ]);
1366
                }
1367
 
1368
 
1369
                if($user->status != User::STATUS_ACTIVE) {
1370
                    return new JsonModel([
1371
                        'success' => false,
1372
                        'data' => [
1373
                            'sync_id' => $sync_id,
1374
                            'message' => 'ERROR_USER_IS_NOT_ACTIVE',
1375
                            'fatal' => true
1376
                        ]
1377
                    ]);
1378
                }
1379
 
1380
                $companyMapper = CompanyMapper::getInstance($this->adapter);
1381
                $company = $companyMapper->fetchOneByUuid($company_uuid);
1382
                if(!$company) {
1383
                    return new JsonModel([
1384
                        'success' => false,
1385
                        'data' => [
1386
                            'sync_id' => $sync_id,
1387
                            'message' => 'ERROR_COMPANY_NOT_FOUND',
1388
                            'fatal' => true
1389
                        ]
1390
                    ]);
1391
                }
1392
 
1393
                if($company->status != Company::STATUS_ACTIVE) {
1394
                    return new JsonModel([
1395
                        'success' => false,
1396
                        'data' => [
1397
                            'sync_id' => $sync_id,
1398
                            'message' => 'ERROR_COMPANY_IS_NOT_FOUND',
1399
                            'fatal' => true
1400
                        ]
1401
                    ]);
1402
                }
1403
 
1404
 
1405
 
1406
 
1407
 
1408
                $companyServiceMapper = CompanyServiceMapper::getInstance($this->adapter);
1409
                $companyService = $companyServiceMapper->fetchOneByCompanyIdAndServiceId($company->id, Service::MICRO_LEARNING);
1410
                if(!$companyService) {
1411
                    return new JsonModel([
1412
                        'success' => false,
1413
                        'data' => [
1414
                            'sync_id' => $sync_id,
1415
                            'message' => 'ERROR_COMPANY_SERVICE_NOT_FOUND',
1416
                            'fatal' => true
1417
                        ]
1418
                    ]);
1419
                }
1420
 
1421
                $serviceActive = true;
1422
                $now = date('Y-m-d H:i:s');
1423
                if($companyService->status == CompanyService::ACTIVE) {
1424
 
1425
                    if($now < $companyService->paid_from || $now > $companyService->paid_to) {
1426
                        $serviceActive = false;
1427
                    }
1428
 
1429
                } else {
1430
                    $serviceActive = false;
1431
                }
1432
 
1433
                if( !$serviceActive) {
1434
                    return new JsonModel([
1435
                        'success' => false,
1436
                        'data' => [
1437
                            'sync_id' => $sync_id,
1438
                            'message' => 'ERROR_COMPANY_SERVICE_IS_NOT_ACTIVE',
1439
                            'fatal' => true
1440
                        ]
1441
                    ]);
1442
                }
1443
 
1444
                $topicMapper = CompanyMicrolearningTopicMapper::getInstance($this->adapter);
1445
                $topic_uuid = isset($data['topic_uuid']) ? filter_var($data['topic_uuid'], FILTER_SANITIZE_STRING) :  '';
1446
                if($topic_uuid) {
1447
                    $topic = $topicMapper->fetchOneByUuid($topic_uuid);
1448
 
1449
                    if(!$topic) {
1450
                        return new JsonModel([
1451
                            'success' => false,
1452
                            'data' => [
1453
                                'sync_id' => $sync_id,
1454
                                'message' => 'ERROR_TOPIC_NOT_FOUND',
1455
                            ]
1456
                        ]);
1457
                    }
1458
 
1459
                    if($topic->company_id != $company->id) {
1460
                        return new JsonModel([
1461
                            'success' => false,
1462
                            'data' => [
1463
                                'sync_id' => $sync_id,
1464
                                'message' => 'ERROR_INVALID_PARAMETERS_TOPIC_COMPANY',
1465
                            ]
1466
                        ]);
1467
                    }
1468
 
1469
                } else {
1470
                    $topic = null;
1471
                }
1472
 
1473
                $capsule_uuid     = isset($data['capsule_uuid']) ? filter_var($data['capsule_uuid'], FILTER_SANITIZE_STRING) :  '';
1474
                $capsuleMapper = CompanyMicrolearningCapsuleMapper::getInstance($this->adapter);
1475
                if($capsule_uuid) {
1476
 
1477
                    $capsule = $capsuleMapper->fetchOneByUuid($capsule_uuid);
1478
                    if(!$capsule) {
1479
                        return new JsonModel([
1480
                            'success' => false,
1481
                            'data' => [
1482
                                'sync_id' => $sync_id,
1483
                                'message' => 'ERROR_CAPSULE_NOT_FOUND',
1484
                            ]
1485
                        ]);
1486
                    }
1487
 
1488
                    if(!$topic || $capsule->topic_id != $topic->id) {
1489
                        return new JsonModel([
1490
                            'success' => false,
1491
                            'data' => [
1492
                                'sync_id' => $sync_id,
1493
                                'message' => 'ERROR_INVALID_PARAMETERS_CAPSULE_TOPIC',
1494
                            ]
1495
                        ]);
1496
                    }
1497
                } else {
1498
                    $capsule = null;
1499
                }
1500
 
1501
                if($capsule) {
1502
 
1503
                    $capsuleActive = true;
1504
                    $capsuleMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
1505
                    $capsuleUser = $capsuleMapper->fetchOneByUserIdAndCapsuleId($user->id, $capsule->id);
1506
 
1507
 
1508
                    $now = date('Y-m-d H:i:s');
1509
                    if($capsuleUser && in_array($capsuleUser->access, [CompanyMicrolearningCapsuleUser::ACCESS_UNLIMITED,CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD ])) {
1510
 
1511
 
1512
                        if($capsuleUser->access == CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD) {
1513
 
1514
                            if($now < $capsuleUser->paid_from || $now > $capsuleUser->paid_to) {
1515
                                $capsuleActive = false;;
1516
                            }
1517
                        }
1518
 
1519
                    } else {
1520
                        $capsuleActive = false;
1521
                    }
1522
 
1523
                    if(!$capsuleActive) {
1524
                        return new JsonModel([
1525
                            'success' => false,
1526
                            'data' => [
1527
                                'sync_id' => $sync_id,
1528
                                'message' => 'ERROR_YOU_DO_NOT_HAVE_ACCESS_TO_THIS_CAPSULE',
1529
                            ]
1530
                        ]);
1531
                    }
1532
                }
1533
 
1534
                $slideMapper = CompanyMicrolearningSlideMapper::getInstance($this->adapter);
1535
                $slide_uuid      = isset($data['slide_uuid']) ? filter_var($data['slide_uuid'], FILTER_SANITIZE_STRING) :  '';
1536
                if($slide_uuid) {
1537
                    $slide = $slideMapper->fetchOneByUuid($slide_uuid);
1538
                    if(!$slide) {
1539
                        return new JsonModel([
1540
                            'success' => false,
1541
                            'data' => [
1542
                                'sync_id' => $sync_id,
1543
                                'message' => 'ERROR_SLIDE_NOT_FOUND',
1544
                            ]
1545
                        ]);
1546
                    }
1547
 
1548
                    if(!$capsule || $slide->capsule_id != $capsule->id) {
1549
                        return new JsonModel([
1550
                            'success' => false,
1551
                            'data' => [
1552
                                'sync_id' => $sync_id,
1553
                                'message' => 'ERROR_INVALID_PARAMETERS_SLIDE_CAPSULE',
1554
                            ]
1555
                        ]);
1556
                    }
1557
                } else {
1558
                    $slide = null;
1559
                }
1560
 
1561
                if($sync_type == 'microlearning-quiz') {
1562
                    $ok = true;
1563
 
1564
                    $quiz_uuid = isset($data['quiz_uuid']) ? $data['quiz_uuid'] : '';
1565
                    $quizMapper = CompanyMicrolearningQuizMapper::getInstance($this->adapter);
1566
 
1567
                    $quiz = $quizMapper->fetchOneByUuid($quiz_uuid);
1568
                    if(!$quiz) {
1569
                        return new JsonModel([
1570
                            'success' => false,
1571
                            'data' => [
1572
                                'sync_id' => $sync_id,
1573
                                'message' => 'ERROR_SLIDE_NOT_FOUND',
1574
                            ]
1575
                        ]);
1576
                    }
1577
 
1578
                    if(!$capsule || $slide->capsule_id != $capsule->id) {
1579
                        return new JsonModel([
1580
                            'success' => false,
1581
                            'data' => [
1582
                                'sync_id' => $sync_id,
1583
                                'message' => 'ERROR_INVALID_PARAMETERS_QUIZ_SLIDE',
1584
                            ]
1585
                        ]);
1586
                    }
1587
 
1588
                    $added_on   = isset($data['added_on'])      ? filter_var($data['added_on'], FILTER_SANITIZE_STRING)  :  '';
1589
 
1590
                    $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
1591
                    if(!$dt) {
1592
                        $ok = false;
1593
                    } else {
1594
                        $added_on = $dt->format('Y-m-d H:i:s');
1595
                    }
1596
 
1597
 
1598
                    if(isset($data['points'])) {
1599
                        $points = intval($data['points'], 10);
1600
                    } else {
1601
                        $ok = false;
1602
                    }
1603
 
1604
 
1605
                    if(isset($data['pass'])) {
1606
                        $status = $data['pass'] == 'yes' ? CompanyMicrolearningUserQuiz::STATUS_PASS : CompanyMicrolearningUserQuiz::STATUS_FAIL;
1607
                    } else {
1608
                        $ok = false;
1609
                    }
1610
 
1611
 
1612
                    if(!$ok) {
1613
                        return new JsonModel([
1614
                            'success' => false,
1615
                            'data' => [
1616
                                'sync_id' => $sync_id,
1617
                                'message' => 'ERROR_INVALID_PARAMETERS',
1618
                            ]
1619
                        ]);
1620
                    }
1621
 
1622
 
1623
                    $array_response = [];
1624
                    $response = isset($data['response']) ? intval($data['response'], 10) : 0;
1625
                    for($i = 0; $i < $response; $i++)
1626
                    {
1627
                        $question_uuid = isset($data["response_{$i}_question_uuid"]) ? $data["response_{$i}_question_uuid"] : '';
1628
                        $answer_uuid = isset($data["response_{$i}_answer_uuid"]) ? $data["response_{$i}_answer_uuid"] : '';
1629
                        $value = isset($data["response_{$i}_value"]) ?  intval($data["response_{$i}_value"], 10) : 0;
1630
                        $points = isset($data["response_{$i}_points"]) ?  intval($data["response_{$i}_points"], 10) : 0;
1631
 
1632
                        if($question_uuid && $answer_uuid)
1633
                        {
1634
                            array_push($array_response, [
1635
                                'question_uuid' => $question_uuid,
1636
                                'answer_uuid' => $answer_uuid,
1637
                                'value' => $value,
1638
                                'points' => $points
1639
 
1640
                            ]);
1641
                        }
1642
 
1643
 
1644
                    }
1645
 
1646
 
1647
                    $userQuiz = new CompanyMicrolearningUserQuiz();
1648
                    $userQuiz->company_id = $company->id;
1649
                    $userQuiz->topic_id = $topic->id;
1650
                    $userQuiz->capsule_id = $capsule->id;
1651
                    $userQuiz->slide_id = $slide->id;
1652
                    $userQuiz->quiz_id = $quiz->id;
1653
                    $userQuiz->user_id = $user->id;
1654
                    $userQuiz->added_on = $added_on;
1655
                    $userQuiz->points = $points;
1656
                    $userQuiz->status = $status;
1657
                    $userQuiz->response = json_encode($array_response);
1658
 
1659
                    $userQuizMapper = CompanyMicrolearningUserQuizMapper::getInstance($this->adapter);
1660
 
1661
                    if($userQuizMapper->insert($userQuiz)) {
1662
                        return new JsonModel([
1663
                            'success' => true,
1664
                            'data' => [
1665
                                'sync_id' => $sync_id
1666
                            ]
1667
                        ]);
1668
                    } else {
1669
                        return new JsonModel([
1670
                            'success' => false,
1671
                            'data' => [
1672
                                'sync_id' => $sync_id,
1673
                                'message' => $userQuizMapper->getError()
1674
                            ]
1675
                        ]);
1676
                    }
1677
 
1678
                }
1679
 
1680
 
1681
                if($sync_type == 'microlearning-progress') {
1682
                    $ok = true;
1683
 
1684
                    $type = isset($data['type']) ? $data['type'] : '';
1685
                    switch($type)
1686
                    {
1687
                        case CompanyMicrolearningUserProgress::TYPE_TOPIC :
1688
                            if(!$topic) {
1689
                                $ok = false;
1690
                            }
1691
                            break;
1692
 
1693
                        case CompanyMicrolearningUserProgress::TYPE_CAPSULE :
1694
                            if(!$topic || !$capsule) {
1695
                                $ok = false;
1696
                            }
1697
                            break;
1698
 
1699
                        case CompanyMicrolearningUserProgress::TYPE_SLIDE :
1700
                            if(!$topic || !$capsule || !$slide) {
1701
                                $ok = false;
1702
                            }
1703
                            break;
1704
 
1705
                        default :
1706
                            $ok = false;
1707
                            break;
1708
 
1709
                    }
1710
 
1711
 
1712
                    $added_on   = isset($data['added_on'])      ? filter_var($data['added_on'], FILTER_SANITIZE_STRING)  :  '';
1713
                    $updated_on = isset($data['updated_on'])    ? filter_var($data['updated_on'], FILTER_SANITIZE_STRING) :  '';
1714
 
1715
                    $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
1716
                    if(!$dt) {
1717
                        $ok = false;
1718
                    } else {
1719
                        $added_on = $dt->format('Y-m-d H:i:s');
1720
                    }
1721
 
1722
                    $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $updated_on );
1723
                    if(!$dt) {
1724
                        $ok = false;
1725
                    } else {
1726
                        $updated_on = $dt->format('Y-m-d H:i:s');
1727
                    }
1728
 
1729
                    if(!$ok) {
1730
                        return new JsonModel([
1731
                            'success' => false,
1732
                            'data' => [
1733
                                'sync_id' => $sync_id,
1734
                                'message' => 'ERROR_INVALID_PARAMETERS',
1735
                            ]
1736
                        ]);
1737
                    }
1738
 
1739
                           //$progress                   = isset($data['progress'])                  ? floatval($data['progress']) :  0;
1740
                    //$total_slides               = isset($data['total_slides'])              ? intval($data['total_slides'], 10) :  0;
1741
                    //$view_slides                = isset($data['view_slides'])               ? intval($data['view_slides'], 10) :  0;
1742
                    $returning                  = isset($data['returning'])                 ? intval($data['returning'], 10) :  0;
1743
                    $returning_after_completed  = isset($data['returning_after_completed']) ? intval($data['returning_after_completed'], 10) :  0;
1744
                    $completed                  = isset($data['completed'])                 ? intval($data['completed'], 10) :  0;
1745
 
1746
                    $progressMapper = CompanyMicrolearningUserProgressMapper::getInstance($this->adapter);
1747
                    $recordProgress = null;
1748
                    switch($type) {
1749
                        case CompanyMicrolearningUserProgress::TYPE_TOPIC  :
1750
                            $recordProgress = $progressMapper->fetchOneByUserIdAndTopicId($user->id, $topic->id);
1751
 
1752
                            break;
1753
 
1754
                        case CompanyMicrolearningUserProgress::TYPE_CAPSULE  :
1755
                            $recordProgress = $progressMapper->fetchOneByUseridAndCapsuleId($user->id, $capsule->id);
1756
                            break;
1757
 
1758
                        case CompanyMicrolearningUserProgress::TYPE_SLIDE  :
1759
                            $recordProgress = $progressMapper->fetchOneByUserIdAndSlideId($user->id, $slide->id);
1760
                            break;
1761
 
1762
                        default :
1763
                            $recordProgress= null;
1764
                    }
1765
 
1766
 
1767
                    if(!$recordProgress) {
1768
                        $recordProgress = new CompanyMicrolearningUserProgress();
1769
 
1770
                        $recordProgress->user_id    = $user->id;
1771
                        $recordProgress->type       = $type;
1772
                        $recordProgress->company_id = $topic->company_id;
1773
                        $recordProgress->topic_id   = $topic->id;
1774
                        $recordProgress->capsule_id = $capsule ? $capsule->id : null;
1775
                        $recordProgress->slide_id   = $slide ? $slide->id : null;
1776
                        $recordProgress->added_on   = $added_on;
1777
                    }
1778
                    $recordProgress->returning                  = $returning;
1779
                    $recordProgress->returning_after_completed  = $returning_after_completed;
1780
                    $recordProgress->completed                  = $completed;
1781
 
1782
                    if($type == CompanyMicrolearningUserProgress::TYPE_TOPIC ) {
1783
 
1784
                        $capsule_ids = [];
1785
                        $companyMicrolearningCapsuleUser = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
1786
                        $records =  $companyMicrolearningCapsuleUser->fetchAllActiveByUserId($user->id);
1787
                        foreach($records as $record)
1788
                        {
1789
                            if($now >= $record->paid_from || $now <= $capsuleUser->paid_to) {
1790
                                if(!in_array($record->capsule_id, $capsule_ids)) {
1791
                                    array_push($capsule_ids, $record->capsule_id);
1792
                                }
1793
                            }
1794
                        }
1795
 
1796
                        $view_slides    = 0;
1797
                        $total_slides   = 0;
1798
                        foreach($capsule_ids as $capsule_id)
1799
                        {
1800
                            $view_slides    += $progressMapper->fetchCountAllSlideViewedByUserIdAndCapsuleId($user->id, $capsule_id);
1801
                            $total_slides   += $slideMapper->fetchTotalCountByCompanyIdAndTopicIdAndCapsuleId($topic->company_id, $topic->id, $capsule_id);
1802
 
1803
                        }
1804
 
1805
 
1806
                        $recordProgress->progress       = $total_slides > 0 ? (($view_slides * 100) / $total_slides) : 0;
1807
                        $recordProgress->total_slides   = $total_slides;
1808
                        $recordProgress->view_slides    = $view_slides;
1809
                    }
1810
                    else if($type == CompanyMicrolearningUserProgress::TYPE_CAPSULE ) {
1811
                        $view_slides    = $progressMapper->fetchCountAllSlideViewedByUserIdAndCapsuleId($user->id, $capsule->id);
1812
                        $total_slides   = $slideMapper->fetchTotalCountByCompanyIdAndTopicIdAndCapsuleId($topic->company_id, $capsule->topic_id, $capsule->id);
1813
 
1814
                        $recordProgress->progress       = $total_slides > 0 ? (($view_slides * 100) / $total_slides) : 0;
1815
                        $recordProgress->total_slides   = $total_slides;
1816
                        $recordProgress->view_slides    = $view_slides;
1817
                    }
1818
                    else {
1819
                        $recordProgress->progress       = 0;
1820
                        $recordProgress->total_slides   = 0;
1821
                        $recordProgress->view_slides    = 0;
1822
                    }
1823
 
1824
                    $recordProgress->updated_on = $updated_on;
1825
 
1826
 
1827
 
1828
                    if($recordProgress->id) {
1829
                        $result = $progressMapper->update($recordProgress);
1830
                    } else {
1831
                        $result = $progressMapper->insert($recordProgress);
1832
                    }
1833
 
1834
                    if($result) {
1835
                        return new JsonModel([
1836
                            'success' => true,
1837
                            'data' => [
1838
                                'sync_id' => $sync_id
1839
                            ]
1840
                        ]);
1841
                    } else {
1842
                        return new JsonModel([
1843
                            'success' => false,
1844
                            'data' => [
1845
                                'sync_id' => $sync_id,
1846
                                'message' => $progressMapper->getError()
1847
                            ]
1848
                        ]);
1849
                    }
1850
                }
1851
 
1852
 
1853
 
1854
                if($sync_type == 'microlearning-userlog') {
1855
                    $activity   = isset($data['activity'])      ? filter_var($data['activity'], FILTER_SANITIZE_STRING)  :  '';
1856
                    $added_on   = isset($data['added_on'])      ? filter_var($data['added_on'], FILTER_SANITIZE_STRING)  :  '';
1857
 
1858
 
1859
                    if(empty($activity)) {
1860
                        $ok = false;
1861
                    }
1862
 
1863
                    $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
1864
                    if(!$dt) {
1865
                        $ok = false;
1866
                    } else {
1867
                        $added_on = $dt->format('Y-m-d H:i:s');
1868
                    }
1869
 
1870
                    if(!$ok) {
1871
                        return new JsonModel([
1872
                            'success' => false,
1873
                            'data' => [
1874
                                'sync_id' => $sync_id,
1875
                                'message' => 'ERROR_INVALID_PARAMETERS',
1876
                            ]
1877
                        ]);
1878
                    }
1879
 
1880
                    $userLog = new CompanyMicrolearningUserLog();
1881
                    $userLog->activity      = $activity;
1882
                    $userLog->user_id       = $user->id;
1883
                    $userLog->company_id    = $topic->company_id;
1884
                    $userLog->topic_id      = $topic->id;
1885
                    $userLog->capsule_id    = $capsule ? $capsule->id : null;
1886
                    $userLog->slide_id      = $slide ? $slide->id : null;
1887
                    $userLog->added_on      = $added_on;
1888
 
1889
 
1890
 
1891
                    $userLogMapper = CompanyMicrolearningUserLogMapper::getInstance($this->adapter);
1892
                    if($userLogMapper->insert($userLog)) {
1893
                        return new JsonModel([
1894
                            'success' => true,
1895
                            'data' => [
1896
                                'sync_id' => $sync_id
1897
                            ]
1898
                        ]);
1899
                    } else {
1900
                        return new JsonModel([
1901
                            'success' => false,
1902
                            'data' => [
1903
                                'sync_id' => $sync_id,
1904
                                'message' => $userLogMapper->getError()
1905
                            ]
1906
                        ]);
1907
                    }
1908
                }
1909
 
1910
            }
1911
 
1912
 
1913
 
1914
 
1915
            if($user_uuid && $sync_type == 'userlog' && $device->application_id = Application::TWOGETSKILLS) {
1916
 
1917
                $userMapper = UserMapper::getInstance($this->adapter);
1918
                $user = $userMapper->fetchOneByUuid($user_uuid);
1919
 
1920
                if(!$user) {
1921
                    return new JsonModel([
1922
                        'success' => false,
1923
                        'data' => [
1924
                            'sync_id' => $sync_id,
1925
                            'message' => 'ERROR_USER_NOT_FOUND',
1926
                            'fatal' => true
1927
                        ]
1928
                    ]);
1929
                }
1930
 
1931
 
1932
                if($user->status != User::STATUS_ACTIVE) {
1933
                    return new JsonModel([
1934
                        'success' => false,
1935
                        'data' => [
1936
                            'sync_id' => $sync_id,
1937
                            'message' => 'ERROR_USER_IS_NOT_ACTIVE',
1938
                            'fatal' => true
1939
                        ]
1940
                    ]);
1941
                }
1942
 
1943
                $activity   = isset($data['activity'])      ? filter_var($data['activity'], FILTER_SANITIZE_STRING)  :  '';
1944
                $added_on   = isset($data['added_on'])      ? filter_var($data['added_on'], FILTER_SANITIZE_STRING)  :  '';
1945
 
1946
                if(empty($activity)) {
1947
                    $ok = false;
1948
                }
1949
 
1950
                $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
1951
                if(!$dt) {
1952
                    $ok = false;
1953
                } else {
1954
                    $added_on = $dt->format('Y-m-d H:i:s');
1955
                }
1956
 
1957
                if(!$ok) {
1958
                    return new JsonModel([
1959
                        'success' => false,
1960
                        'data' => [
1961
                            'sync_id' => $sync_id,
1962
                            'message' => 'ERROR_INVALID_PARAMETERS',
1963
                        ]
1964
                    ]);
1965
                }
1966
 
1967
                $userLog = new CompanyMicrolearningUserLog();
1968
                $userLog->company_id = null;
1969
                $userLog->user_id = $user->id;
1970
                $userLog->activity = $activity;
1971
                $userLog->added_on = $added_on;
1972
 
1973
 
1974
                $userLogMapper = CompanyMicrolearningUserLogMapper::getInstance($this->adapter);
1975
                if($userLogMapper->insert($userLog)) {
1976
                    return new JsonModel([
1977
                        'success' => true,
1978
                        'data' => [
1979
                            'sync_id' => $sync_id
1980
                        ]
1981
                    ]);
1982
                } else {
1983
                    return new JsonModel([
1984
                        'success' => false,
1985
                        'data' => [
1986
                            'sync_id' => $sync_id,
1987
                            'message' => $userLogMapper->getError()
1988
                        ]
1989
                    ]);
1990
                }
1991
            }
1992
 
1993
            return new JsonModel([
1994
                'success' => true,
1995
                'data' => [
1996
                    'sync_id' => $sync_id
1997
                ]
1998
            ]);
1999
 
2000
        }
2001
 
2002
        return new JsonModel([
2003
            'success' => false,
2004
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
2005
        ]);
2006
    }
2007
 
2008
 
2009
    public function syncBatchAction()
2010
    {
2011
        $request = $this->getRequest();
2012
 
2013
        if($request->isPost()) {
2014
 
2015
            $rawdata = file_get_contents("php://input");
2016
            error_log('$rawdata = ' . $rawdata );
2017
 
2018
 
2019
            $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
2020
 
2021
            $device_uuid = filter_var($this->params()->fromPost('device_uuid', ''), FILTER_SANITIZE_STRING);
2022
            $max_records = filter_var($this->params()->fromPost('max_records', 0), FILTER_SANITIZE_NUMBER_INT);
2023
 
2024
 
2025
 
2026
            error_log('device_uuid = ' . $device_uuid . ' max_records = ' . $max_records);
2027
 
2028
            $ok = $device_uuid && strlen($device_uuid) == 36 && $max_records;
2029
 
2030
            if(!$ok) {
2031
                return new JsonModel([
2032
                    'success' => false,
2033
                    'data' => 'ERROR_PARAMETERS_ARE_INVALID',
2034
                ]);
2035
            }
2036
 
2037
            $deviceMapper = DeviceMapper::getInstance($this->adapter);
2038
            $device = $deviceMapper->fetchOne($device_uuid);
2039
 
2040
 
2041
            if(!$device) {
2042
                return new JsonModel([
2043
                    'success' => false,
2044
                    'data' => 'ERROR_DEVICE_NOT_FOUND'
2045
                ]);
2046
            } else {
2047
                $device->ip = Functions::getUserIP();
2048
                $deviceMapper->update($device);
2049
            }
2050
 
2051
            $result_sync_ids = [];
2052
 
2053
 
2054
 
2055
 
16 efrain 2056
            $users = [];
2057
            $companies = [];
2058
            $company_services = [];
2059
            $topics = [];
2060
            $capsules = [];
2061
            $capsule_users = [];
2062
            $slides = [];
2063
            $quizzes = [];
2064
            $questions = [];
2065
            $answers = [];
2066
 
2067
            $userMapper = UserMapper::getInstance($this->adapter);
2068
            $companyMapper = CompanyMapper::getInstance($this->adapter);
2069
            $companyServiceMapper = CompanyServiceMapper::getInstance($this->adapter);
2070
            $topicMapper = CompanyMicrolearningTopicMapper::getInstance($this->adapter);
2071
            $capsuleMapper = CompanyMicrolearningCapsuleMapper::getInstance($this->adapter);
2072
            $capsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
2073
            $slideMapper = CompanyMicrolearningSlideMapper::getInstance($this->adapter);
2074
            $quizMapper = CompanyMicrolearningQuizMapper::getInstance($this->adapter);
2075
            $questionMapper = CompanyMicrolearningQuestionMapper::getInstance($this->adapter);
2076
            $answerMapper = CompanyMicrolearningAnswerMapper::getInstance($this->adapter);
2077
 
2078
 
2079
            $userProgressMapper = CompanyMicrolearningUserProgressMapper::getInstance($this->adapter);
2080
            $userLogMapper = CompanyMicrolearningUserLogMapper::getInstance($this->adapter);
2081
 
1 www 2082
            for($i = 1; $i <= $max_records; $i++)
2083
            {
2084
                $sync_id        = filter_var($this->params()->fromPost('record_sync_id' . $i, ''), FILTER_SANITIZE_NUMBER_INT);
2085
                $record_data    = $this->params()->fromPost('record_data' . $i, '');
2086
 
2087
                if(empty($record_data) || empty($sync_id )) {
2088
                    continue;
2089
                }
2090
 
2091
                $record         = json_decode($record_data, true);
2092
                $sync_type      = isset($record['sync_type']) ? filter_var($record['sync_type'],  FILTER_SANITIZE_STRING) : '';
2093
                $user_uuid      = isset($record['user_uuid']) ? filter_var($record['user_uuid'],  FILTER_SANITIZE_STRING) : '';
2094
                $company_uuid   = isset($record['company_uuid']) ? filter_var($record['company_uuid'], FILTER_SANITIZE_STRING) : '';
2095
 
2096
                if(!$sync_id) {
2097
                    continue;
2098
                }
2099
 
2100
                /***** INICIO MICROLEARNING *****/
2101
 
2102
                if($user_uuid && $device->application_id = Application::TWOGETSKILLS  && $company_uuid && in_array($sync_type, ['microlearning-progress', 'microlearning-userlog', 'microlearning-quiz'])) {
2103
 
16 efrain 2104
 
2105
                    if(isset($users[$user_uuid])) {
2106
                        $user = $users[$user_uuid];
2107
                    } else {
2108
 
2109
                        $user = $userMapper->fetchOneByUuid($user_uuid);
2110
                        if($user) {
2111
                            $users[$user_uuid] = $user;
2112
                        }
2113
                    }
2114
 
2115
 
1 www 2116
                    if(!$user) {
2117
                        array_push($result_sync_ids, [
2118
                            'success' => false,
2119
                            'sync_id' => $sync_id,
2120
                            'message' => 'ERROR_USER_NOT_FOUND',
2121
                            'fatal' => true
2122
                        ]);
2123
                        continue;
2124
                    }
2125
 
2126
 
2127
                    if($user->status != User::STATUS_ACTIVE) {
2128
                        array_push($result_sync_ids, [
2129
                            'success' => false,
2130
                            'sync_id' => $sync_id,
2131
                            'message' => 'ERROR_USER_IS_NOT_ACTIVE',
2132
                            'fatal' => true
2133
                        ]);
2134
                        continue;
2135
                    }
2136
 
16 efrain 2137
 
2138
                    if(isset($companies[$company_uuid])) {
2139
                        $company = $companies[$company_uuid];
2140
                    } else {
2141
                        $company = $companyMapper->fetchOneByUuid($company_uuid);
2142
                        if($company) {
2143
                            $companies[$company_uuid] = $company;
2144
                        }
2145
                    }
2146
 
2147
 
2148
 
2149
 
1 www 2150
                    if(!$company) {
2151
                        array_push($result_sync_ids, [
2152
                            'success' => false,
2153
                            'sync_id' => $sync_id,
2154
                            'message' => 'ERROR_COMPANY_NOT_FOUND',
2155
                            'fatal' => true
2156
                        ]);
2157
                        continue;
2158
                    }
2159
 
2160
                    if($company->status != Company::STATUS_ACTIVE) {
2161
                        array_push($result_sync_ids, [
2162
                            'success' => false,
2163
                            'sync_id' => $sync_id,
2164
                            'message' => 'ERROR_COMPANY_IS_NOT_FOUND',
2165
                            'fatal' => true
2166
                        ]);
2167
                        continue;
2168
                    }
2169
 
2170
 
2171
 
16 efrain 2172
                    $key = $company->id . '-' .  Service::MICRO_LEARNING;
2173
                    if(isset($company_services[$key])) {
2174
                        $companyService = $company_services[$key];
2175
                    } else {
2176
                        $companyService = $companyServiceMapper->fetchOneByCompanyIdAndServiceId($company->id, Service::MICRO_LEARNING);
2177
                        if($companyService) {
2178
                            $company_services[$key] = $companyService;
2179
                        }
2180
                    }
1 www 2181
 
2182
                    if(!$companyService) {
2183
                        array_push($result_sync_ids, [
2184
                            'success' => false,
2185
                            'sync_id' => $sync_id,
2186
                            'message' => 'ERROR_COMPANY_SERVICE_NOT_FOUND',
2187
                            'fatal' => true
2188
                        ]);
2189
                        continue;
2190
                    }
2191
 
2192
                    $serviceActive = true;
2193
                    $now = date('Y-m-d H:i:s');
2194
                    if($companyService->status == CompanyService::ACTIVE) {
2195
 
2196
                        if($now < $companyService->paid_from || $now > $companyService->paid_to) {
2197
                            $serviceActive = false;
2198
                        }
2199
 
2200
                    } else {
2201
                        $serviceActive = false;
2202
                    }
2203
 
2204
                    if( !$serviceActive) {
2205
                        array_push($result_sync_ids, [
2206
                            'success' => false,
2207
                            'sync_id' => $sync_id,
2208
                            'message' => 'ERROR_COMPANY_SERVICE_IS_NOT_ACTIVE',
2209
                            'fatal' => true
2210
                        ]);
2211
                        continue;
2212
                    }
2213
 
16 efrain 2214
 
1 www 2215
                    $topic_uuid = isset($record['topic_uuid']) ? filter_var($record['topic_uuid'], FILTER_SANITIZE_STRING) :  '';
2216
                    if($topic_uuid) {
2217
 
16 efrain 2218
                        if(isset($topics[$topic_uuid])) {
2219
                            $topic = $topics[$topic_uuid];
2220
                        } else {
2221
                            $topic = $topicMapper->fetchOneByUuid($topic_uuid);
2222
                            if($topic) {
2223
                                $topics[$topic_uuid] = $topic;
2224
                            }
2225
                        }
2226
 
1 www 2227
                        if(!$topic) {
2228
                            array_push($result_sync_ids, [
2229
                                'success' => false,
2230
                                'sync_id' => $sync_id,
2231
                                'message' => 'ERROR_TOPIC_NOT_FOUND',
2232
                            ]);
2233
                            continue;
2234
                        }
2235
 
2236
                        if($topic->company_id != $company->id) {
2237
                            array_push($result_sync_ids, [
2238
                                'success' => false,
2239
                                'sync_id' => $sync_id,
2240
                                'message' => 'ERROR_INVALID_PARAMETERS_TOPIC_COMPANY',
2241
                            ]);
2242
                            continue;
2243
                        }
2244
 
2245
                    } else {
2246
                        $topic = null;
2247
                    }
2248
 
2249
                    $capsule_uuid     = isset($record['capsule_uuid']) ? filter_var($record['capsule_uuid'], FILTER_SANITIZE_STRING) :  '';
16 efrain 2250
 
1 www 2251
                    if($capsule_uuid) {
2252
 
16 efrain 2253
                        if(isset($capsules[$capsule_uuid])) {
2254
                            $capsule = $capsules[$capsule_uuid];
2255
                        } else {
2256
                            $capsule = $capsuleMapper->fetchOneByUuid($capsule_uuid);
2257
                            if($capsule) {
2258
                                $capsules[$capsule_uuid] = $capsule;
2259
                            }
2260
                        }
1 www 2261
                        if(!$capsule) {
2262
                            array_push($result_sync_ids, [
2263
                                'success' => false,
2264
                                'sync_id' => $sync_id,
2265
                                'message' => 'ERROR_CAPSULE_NOT_FOUND',
2266
                            ]);
2267
                            continue;
2268
                        }
2269
 
2270
                        if(!$topic || $capsule->topic_id != $topic->id) {
2271
                            array_push($result_sync_ids, [
2272
                                'success' => false,
2273
                                'sync_id' => $sync_id,
2274
                                'message' => 'ERROR_INVALID_PARAMETERS_CAPSULE_TOPIC',
2275
                            ]);
2276
                            continue;
2277
                        }
2278
                    } else {
2279
                        $capsule = null;
2280
                    }
2281
 
2282
                    if($capsule) {
2283
 
2284
                        $capsuleActive = true;
2285
 
16 efrain 2286
                        $key = $user->id . '-' . $capsule->id;
1 www 2287
 
16 efrain 2288
                        if(isset($capsule_users[$key])) {
2289
                            $capsuleUser = $capsule_users[$key];
2290
                        } else {
2291
 
2292
                            $capsuleUser = $capsuleUserMapper->fetchOneByUserIdAndCapsuleId($user->id, $capsule->id);
2293
                            if($capsuleUser) {
2294
                                $capsule_users[$key] = $capsuleUser;
2295
                            }
2296
 
2297
                        }
2298
 
1 www 2299
                        $now = date('Y-m-d H:i:s');
2300
                        if($capsuleUser && in_array($capsuleUser->access, [CompanyMicrolearningCapsuleUser::ACCESS_UNLIMITED,CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD ])) {
2301
 
2302
 
2303
                            if($capsuleUser->access == CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD) {
2304
 
2305
                                if($now < $capsuleUser->paid_from || $now > $capsuleUser->paid_to) {
2306
                                    $capsuleActive = false;;
2307
                                }
2308
                            }
2309
 
2310
                        } else {
2311
                            $capsuleActive = false;
2312
                        }
2313
 
2314
                        if(!$capsuleActive) {
2315
                            array_push($result_sync_ids, [
2316
                                'success' => false,
2317
                                'sync_id' => $sync_id,
2318
                                'message' => 'ERROR_YOU_DO_NOT_HAVE_ACCESS_TO_THIS_CAPSULE',
2319
                            ]);
2320
                            continue;
2321
                        }
2322
                    }
2323
 
16 efrain 2324
 
1 www 2325
                    $slide_uuid      = isset($record['slide_uuid']) ? filter_var($record['slide_uuid'], FILTER_SANITIZE_STRING) :  '';
2326
                    if($slide_uuid) {
16 efrain 2327
 
2328
                        if(isset($slides[$slide_uuid])) {
2329
                            $slide = $slides[$slide_uuid];
2330
                        } else {
2331
 
2332
                            $slide = $slideMapper->fetchOneByUuid($slide_uuid);
2333
                            if($slide) {
2334
                                $slides[$slide_uuid] = $slide;
2335
                            }
2336
                        }
1 www 2337
                        if(!$slide) {
2338
                            array_push($result_sync_ids, [
2339
                                'success' => false,
2340
                                'sync_id' => $sync_id,
2341
                                'message' => 'ERROR_SLIDE_NOT_FOUND',
2342
                            ]);
2343
                            continue;
2344
                        }
2345
 
2346
                        if(!$capsule || $slide->capsule_id != $capsule->id) {
2347
                            array_push($result_sync_ids, [
2348
                                'success' => false,
2349
                                'sync_id' => $sync_id,
2350
                                'message' => 'ERROR_INVALID_PARAMETERS_SLIDE_CAPSULE',
2351
                            ]);
2352
                            continue;
2353
                        }
2354
                    } else {
2355
                        $slide = null;
2356
                    }
2357
 
2358
                    if($sync_type == 'microlearning-quiz') {
2359
                        $ok = true;
2360
 
2361
                        $quiz_uuid = isset($record['quiz_uuid']) ? $record['quiz_uuid'] : '';
16 efrain 2362
 
2363
                        if(isset($quizzes[$quiz_uuid])) {
2364
                            $quiz = $quizzes[$quiz_uuid];
2365
                        } else {
2366
                            $quiz = $quizMapper->fetchOneByUuid($quiz_uuid);
2367
                            if($quiz) {
2368
                                $quizzes[$quiz_uuid] = $quiz;
2369
                            }
2370
                        }
1 www 2371
                        if(!$quiz) {
2372
                            array_push($result_sync_ids, [
2373
                                'success' => false,
2374
                                'sync_id' => $sync_id,
2375
                                'message' => 'ERROR_SLIDE_NOT_FOUND',
2376
                            ]);
2377
                            continue;
2378
                        }
2379
 
2380
                        if(!$capsule || $slide->capsule_id != $capsule->id) {
2381
                            array_push($result_sync_ids, [
2382
                                'success' => false,
2383
                                'sync_id' => $sync_id,
2384
                                'message' => 'ERROR_INVALID_PARAMETERS_QUIZ_SLIDE',
2385
                            ]);
2386
                            continue;
2387
                        }
2388
 
2389
                        $added_on   = isset($record['added_on'])      ? filter_var($record['added_on'], FILTER_SANITIZE_STRING)  :  '';
2390
 
2391
                        $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
2392
                        if(!$dt) {
2393
                            $ok = false;
2394
                        } else {
2395
                            $added_on = $dt->format('Y-m-d H:i:s');
2396
                        }
2397
 
2398
                        if(isset($record['points'])) {
2399
                            $points = intval($record['points'], 10);
2400
                        } else {
2401
                            $ok = false;
2402
                        }
2403
 
2404
                        if(isset($record['pass'])) {
2405
                            $status = $record['pass'] == 'yes' ? CompanyMicrolearningUserQuiz::STATUS_PASS : CompanyMicrolearningUserQuiz::STATUS_FAIL;
2406
                        } else {
2407
                            $ok = false;
2408
                        }
2409
 
2410
                        if(!$ok) {
2411
                            array_push($result_sync_ids, [
2412
                                'success' => false,
2413
                                'sync_id' => $sync_id,
2414
                                'message' => 'ERROR_INVALID_PARAMETERS',
2415
                            ]);
2416
                            continue;
2417
                        }
2418
 
2419
                        $array_response = [];
2420
                        $response = isset($record['response']) ? intval($record['response'], 10) : 0;
2421
                        for($i = 0; $i < $response; $i++)
2422
                        {
2423
                            $question_uuid = isset($record["response_{$i}_question_uuid"]) ? $record["response_{$i}_question_uuid"] : '';
2424
                            $answer_uuid = isset($record["response_{$i}_answer_uuid"]) ? $record["response_{$i}_answer_uuid"] : '';
2425
                            $value = isset($record["response_{$i}_value"]) ?  intval($record["response_{$i}_value"], 10) : 0;
2426
                            $points = isset($record["response_{$i}_points"]) ?  intval($record["response_{$i}_points"], 10) : 0;
2427
 
16 efrain 2428
 
2429
                            if(isset($questions[$question_uuid])) {
2430
                                $question = $questions[$question_uuid];
2431
                            } else {
2432
                                $question = $questionMapper->fetchOneByUuid($question_uuid);
2433
                                if($question) {
2434
                                    $questions[$question_uuid] = $question;
2435
                                }
2436
                            }
2437
 
2438
                            if(!$question || $question->quiz_id != $quiz->id) {
2439
                                array_push($result_sync_ids, [
2440
                                    'success' => false,
2441
                                    'sync_id' => $sync_id,
2442
                                    'message' => 'ERROR_INVALID_PARAMETERS_QUIZ_QUESTION_SLIDE',
1 www 2443
                                ]);
16 efrain 2444
                                continue;
2445
                            }
2446
 
2447
                            if(isset($answers[$answer_uuid])) {
2448
                                $answer = $answers[$answer_uuid];
2449
                            } else {
2450
                                $answer = $answerMapper->fetchOneByUuid($answer_uuid);
2451
                                if($answer) {
2452
                                    $answers[$answer_uuid] = $answer;
2453
                                }
2454
                            }
2455
 
2456
                            if($answer && $answer->question_id != $question->id) {
2457
                                array_push($result_sync_ids, [
2458
                                    'success' => false,
2459
                                    'sync_id' => $sync_id,
2460
                                    'message' => 'ERROR_INVALID_PARAMETERS_QUIZ_ANSWER_SLIDE',
2461
                                ]);
2462
                                continue;
2463
                            }
2464
 
2465
                            array_push($array_response, [
2466
                                'question_uuid' => $question_uuid,
2467
                                'answer_uuid' => $answer_uuid,
2468
                                'value' => $value,
2469
                                'points' => $points
2470
                            ]);
1 www 2471
                        }
2472
 
2473
                        $userQuiz = new CompanyMicrolearningUserQuiz();
2474
                        $userQuiz->company_id = $company->id;
2475
                        $userQuiz->topic_id = $topic->id;
2476
                        $userQuiz->capsule_id = $capsule->id;
2477
                        $userQuiz->slide_id = $slide->id;
2478
                        $userQuiz->quiz_id = $quiz->id;
2479
                        $userQuiz->user_id = $user->id;
2480
                        $userQuiz->added_on = $added_on;
2481
                        $userQuiz->points = $points;
2482
                        $userQuiz->status = $status;
2483
                        $userQuiz->response = json_encode($array_response);
2484
 
2485
                        $userQuizMapper = CompanyMicrolearningUserQuizMapper::getInstance($this->adapter);
2486
 
2487
                        if($userQuizMapper->insert($userQuiz)) {
2488
                            array_push($result_sync_ids, [
2489
                                'success' => true,
2490
                                'sync_id' => $sync_id
2491
                            ]);
2492
                        } else {
2493
                            array_push($result_sync_ids, [
2494
                                'success' => false,
2495
                                'sync_id' => $sync_id,
2496
                                'message' => $userQuizMapper->getError()
2497
                            ]);
2498
                        }
2499
                        continue;
2500
                    }
2501
 
2502
                    if($sync_type == 'microlearning-progress') {
2503
                        $ok = true;
2504
 
2505
                        $type = isset($record['type']) ? $record['type'] : '';
2506
                        switch($type)
2507
                        {
2508
                            case CompanyMicrolearningUserProgress::TYPE_TOPIC :
2509
                                if(!$topic) {
2510
                                    $ok = false;
2511
                                }
2512
                                break;
2513
 
2514
                            case CompanyMicrolearningUserProgress::TYPE_CAPSULE :
2515
                                if(!$topic || !$capsule) {
2516
                                    $ok = false;
2517
                                }
2518
                                break;
2519
 
2520
                            case CompanyMicrolearningUserProgress::TYPE_SLIDE :
2521
                                if(!$topic || !$capsule || !$slide) {
2522
                                    $ok = false;
2523
                                }
2524
                                break;
2525
 
2526
                            default :
2527
                                $ok = false;
2528
                                break;
2529
                        }
2530
 
2531
                        $added_on   = isset($record['added_on'])      ? filter_var($record['added_on'], FILTER_SANITIZE_STRING)  :  '';
2532
                        $updated_on = isset($record['updated_on'])    ? filter_var($record['updated_on'], FILTER_SANITIZE_STRING) :  '';
2533
 
2534
                        $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
2535
                        if(!$dt) {
2536
                            $ok = false;
2537
                        } else {
2538
                            $added_on = $dt->format('Y-m-d H:i:s');
2539
                        }
2540
 
2541
                        $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $updated_on );
2542
                        if(!$dt) {
2543
                            $ok = false;
2544
                        } else {
2545
                            $updated_on = $dt->format('Y-m-d H:i:s');
2546
                        }
2547
 
2548
                        if(!$ok) {
2549
                            array_push($result_sync_ids, [
2550
                                'success' => false,
2551
                                'sync_id' => $sync_id,
2552
                                'message' => 'ERROR_INVALID_PARAMETERS',
2553
                            ]);
2554
                            continue;
2555
                        }
2556
 
18 efrain 2557
                        $progress                   = isset($record['progress'])                  ? floatval($record['progress']) :  0;
2558
                        $total_slides               = isset($record['total_slides'])              ? intval($record['total_slides'], 10) :  0;
2559
                        $view_slides                = isset($record['view_slides'])               ? intval($record['view_slides'], 10) :  0;
1 www 2560
                        $returning                  = isset($record['returning'])                 ? intval($record['returning'], 10) :  0;
2561
                        $returning_after_completed  = isset($record['returning_after_completed']) ? intval($record['returning_after_completed'], 10) :  0;
2562
                        $completed                  = isset($record['completed'])                 ? intval($record['completed'], 10) :  0;
2563
 
16 efrain 2564
 
1 www 2565
                        $recordProgress = null;
2566
                        switch($type) {
2567
                            case CompanyMicrolearningUserProgress::TYPE_TOPIC  :
16 efrain 2568
                                $recordProgress = $userProgressMapper->fetchOneByUserIdAndTopicId($user->id, $topic->id);
1 www 2569
 
2570
                                break;
2571
 
2572
                            case CompanyMicrolearningUserProgress::TYPE_CAPSULE  :
16 efrain 2573
                                $recordProgress = $userProgressMapper->fetchOneByUseridAndCapsuleId($user->id, $capsule->id);
1 www 2574
                                break;
2575
 
2576
                            case CompanyMicrolearningUserProgress::TYPE_SLIDE  :
16 efrain 2577
                                $recordProgress = $userProgressMapper->fetchOneByUserIdAndSlideId($user->id, $slide->id);
1 www 2578
                                break;
2579
 
2580
                            default :
2581
                                $recordProgress= null;
2582
                        }
2583
 
2584
 
2585
                        if(!$recordProgress) {
2586
                            $recordProgress = new CompanyMicrolearningUserProgress();
2587
 
2588
                            $recordProgress->user_id    = $user->id;
2589
                            $recordProgress->type       = $type;
2590
                            $recordProgress->company_id = $topic->company_id;
2591
                            $recordProgress->topic_id   = $topic->id;
2592
                            $recordProgress->capsule_id = $capsule ? $capsule->id : null;
2593
                            $recordProgress->slide_id   = $slide ? $slide->id : null;
2594
                            $recordProgress->added_on   = $added_on;
16 efrain 2595
                        } else {
2596
 
2597
                            if($recordProgress->updated_on > $updated_on) {
2598
                                array_push($result_sync_ids, [
2599
                                    'success' => true,
2600
                                    'sync_id' => $sync_id,
2601
                                ]);
2602
                                continue;
2603
                            }
2604
 
2605
 
2606
 
1 www 2607
                        }
2608
                        $recordProgress->returning                  = $returning;
2609
                        $recordProgress->returning_after_completed  = $returning_after_completed;
2610
                        $recordProgress->completed                  = $completed;
2611
 
2612
                        if($type == CompanyMicrolearningUserProgress::TYPE_TOPIC ) {
2613
 
2614
                            $capsule_ids = [];
2615
                            $companyMicrolearningCapsuleUser = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
2616
                            $records =  $companyMicrolearningCapsuleUser->fetchAllActiveByUserId($user->id);
2617
                            foreach($records as $record)
2618
                            {
2619
                                if($now >= $record->paid_from || $now <= $capsuleUser->paid_to) {
2620
                                    if(!in_array($record->capsule_id, $capsule_ids)) {
2621
                                        array_push($capsule_ids, $record->capsule_id);
2622
                                    }
2623
                                }
2624
                            }
18 efrain 2625
 
2626
                            $recordProgress->progress       = $progress;
1 www 2627
                            $recordProgress->total_slides   = $total_slides;
2628
                            $recordProgress->view_slides    = $view_slides;
2629
                        }
2630
                        else if($type == CompanyMicrolearningUserProgress::TYPE_CAPSULE ) {
18 efrain 2631
 
2632
                            $recordProgress->progress       = $progress;
1 www 2633
                            $recordProgress->total_slides   = $total_slides;
2634
                            $recordProgress->view_slides    = $view_slides;
2635
                        }
2636
                        else {
2637
                            $recordProgress->progress       = 0;
2638
                            $recordProgress->total_slides   = 0;
2639
                            $recordProgress->view_slides    = 0;
2640
                        }
2641
 
2642
                        $recordProgress->updated_on = $updated_on;
2643
 
2644
 
2645
 
2646
                        if($recordProgress->id) {
16 efrain 2647
                            $result = $userProgressMapper->update($recordProgress);
1 www 2648
                        } else {
16 efrain 2649
                            $result = $userProgressMapper->insert($recordProgress);
1 www 2650
                        }
2651
 
2652
                        if($result) {
2653
                            array_push($result_sync_ids, [
2654
                                'success' => true,
2655
                                'sync_id' => $sync_id
2656
                            ]);
2657
                        } else {
2658
                            array_push($result_sync_ids, [
2659
                                'success' => false,
2660
                                'sync_id' => $sync_id,
16 efrain 2661
                                'message' => $userProgressMapper->getError()
1 www 2662
                            ]);
2663
                        }
2664
                        continue;
2665
                    }
2666
 
2667
 
2668
 
2669
                    if($sync_type == 'microlearning-userlog') {
2670
                        $activity   = isset($record['activity'])      ? filter_var($record['activity'], FILTER_SANITIZE_STRING)  :  '';
2671
                        $added_on   = isset($record['added_on'])      ? filter_var($record['added_on'], FILTER_SANITIZE_STRING)  :  '';
2672
 
2673
 
2674
                        if(empty($activity)) {
2675
                            $ok = false;
2676
                        }
2677
 
2678
                        $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
2679
                        if(!$dt) {
2680
                            $ok = false;
2681
                        } else {
2682
                            $added_on = $dt->format('Y-m-d H:i:s');
2683
                        }
2684
 
2685
                        if(!$ok) {
2686
                            array_push($result_sync_ids, [
2687
                                'success' => false,
2688
                                'sync_id' => $sync_id,
2689
                                'message' => 'ERROR_INVALID_PARAMETERS',
2690
                            ]);
2691
                            continue;
2692
                        }
2693
 
2694
 
2695
 
2696
 
16 efrain 2697
                        $userLog = $userLogMapper->fetchLastBy($user->id);
2698
                        if($userLog) {
2699
                            $insert = $userLog->added_on <= $added_on;
2700
                        } else {
2701
                            $insert = true;
2702
                        }
2703
 
2704
 
2705
                        if($insert) {
2706
 
2707
                            $userLog = new CompanyMicrolearningUserLog();
2708
                            $userLog->activity      = $activity;
2709
                            $userLog->user_id       = $user->id;
2710
                            $userLog->company_id    = $topic->company_id;
2711
                            $userLog->topic_id      = $topic->id;
2712
                            $userLog->capsule_id    = $capsule ? $capsule->id : null;
2713
                            $userLog->slide_id      = $slide ? $slide->id : null;
2714
                            $userLog->added_on      = $added_on;
2715
 
2716
 
2717
 
2718
 
2719
                            if($userLogMapper->insert($userLog)) {
2720
                                array_push($result_sync_ids, [
2721
                                    'success' => true,
2722
                                    'sync_id' => $sync_id
2723
                                ]);
2724
                            } else {
2725
                                array_push($result_sync_ids, [
2726
                                    'success' => false,
2727
                                    'sync_id' => $sync_id,
2728
                                    'message' => $userLogMapper->getError()
2729
                                ]);
2730
                            }
2731
                        } else {
1 www 2732
                            array_push($result_sync_ids, [
2733
                                'success' => true,
16 efrain 2734
                                'sync_id' => $sync_id
1 www 2735
                            ]);
2736
                        }
2737
                        continue;
2738
                    }
2739
 
2740
                }
2741
 
2742
                /***** FIN MICROLEARNING *****/
2743
 
2744
 
2745
                /***** INICIO LOG DE USUARIO GENERAL *****/
2746
 
2747
                if($user_uuid && $sync_type == 'userlog' && $device->application_id = Application::TWOGETSKILLS) {
2748
 
2749
 
16 efrain 2750
                    if(isset($users[$user_uuid])) {
2751
                        $user = $users[$user_uuid];
2752
                    } else {
2753
                        $user = $userMapper->fetchOneByUuid($user_uuid);
2754
                        if($user) {
2755
                            $users[$user_uuid] = $user;
2756
                        }
2757
                    }
2758
 
2759
 
2760
 
2761
 
1 www 2762
                    if(!$user) {
2763
                        array_push($result_sync_ids, [
2764
                            'success' => false,
2765
                            'sync_id' => $sync_id,
2766
                            'message' => 'ERROR_USER_NOT_FOUND',
2767
                            'fatal' => true
2768
                        ]);
2769
                        continue;
2770
                    }
2771
 
2772
 
2773
                    if($user->status != User::STATUS_ACTIVE) {
2774
                        array_push($result_sync_ids, [
2775
                            'success' => false,
2776
                            'sync_id' => $sync_id,
2777
                            'message' => 'ERROR_USER_IS_NOT_ACTIVE',
2778
                            'fatal' => true
2779
                        ]);
2780
                        continue;
2781
                    }
2782
 
2783
                    $activity   = isset($record['activity'])      ? filter_var($record['activity'], FILTER_SANITIZE_STRING)  :  '';
2784
                    $added_on   = isset($record['added_on'])      ? filter_var($record['added_on'], FILTER_SANITIZE_STRING)  :  '';
2785
 
2786
                    if(empty($activity)) {
2787
                        $ok = false;
2788
                    }
2789
 
2790
                    $dt = \DateTime::createFromFormat($serviceDatetimeFormat, $added_on);
2791
                    if(!$dt) {
2792
                        $ok = false;
2793
                    } else {
2794
                        $added_on = $dt->format('Y-m-d H:i:s');
2795
                    }
2796
 
2797
                    if(!$ok) {
2798
                        array_push($result_sync_ids, [
2799
                            'success' => false,
2800
                            'sync_id' => $sync_id,
2801
                            'message' => 'ERROR_INVALID_PARAMETERS',
2802
                        ]);
2803
                        continue;
2804
                    }
2805
 
2806
 
16 efrain 2807
                    $userLog = $userLogMapper->fetchLastBy($user->id);
2808
                    if($userLog) {
2809
                        $insert = $userLog->added_on <= $added_on;
2810
                    } else {
2811
                        $insert = true;
2812
                    }
1 www 2813
 
16 efrain 2814
 
2815
                    if($insert) {
2816
                        $userLog = new CompanyMicrolearningUserLog();
2817
                        $userLog->company_id = null;
2818
                        $userLog->user_id = $user->id;
2819
                        $userLog->activity = $activity;
2820
                        $userLog->added_on = $added_on;
2821
 
2822
 
2823
                        $userLogMapper = CompanyMicrolearningUserLogMapper::getInstance($this->adapter);
2824
                        if($userLogMapper->insert($userLog)) {
2825
                            array_push($result_sync_ids, [
2826
                                'success' => true,
2827
                                'sync_id' => $sync_id
2828
                            ]);
2829
                        } else {
2830
                            array_push($result_sync_ids, [
2831
                                'success' => false,
2832
                                'sync_id' => $sync_id,
2833
                                'message' => $userLogMapper->getError()
2834
                            ]);
2835
                        }
2836
                    } else {
1 www 2837
                        array_push($result_sync_ids, [
2838
                            'success' => true,
2839
                            'sync_id' => $sync_id
2840
                        ]);
2841
                    }
2842
 
16 efrain 2843
 
2844
 
1 www 2845
                    continue;
2846
                }
2847
 
2848
                /***** FIN LOG DE USUARIO GENERAL ******/
2849
            }
2850
 
2851
            if( $result_sync_ids) {
2852
                return new JsonModel([
2853
                    'success' => true,
2854
                    'data' => $result_sync_ids
2855
                ]);
2856
            } else {
2857
                return new JsonModel([
2858
                    'success' => false,
2859
                    'data' => 'ERROR_INVALID_PARAMETERS'
2860
                ]);
2861
            }
2862
 
2863
 
2864
        }
2865
 
2866
        return new JsonModel([
2867
            'success' => false,
2868
            'data' => 'ERROR_METHOD_NOT_ALLOWED'
2869
        ]);
2870
    }
2871
 
2872
    /**
2873
     *
2874
     * @param User $user
2875
     * @param boolean $includeLogs
2876
     * @param boolean $includeProgress
2877
     * @return array[]
2878
     */
2879
    private function getSyncData($user, $includeLogs = true, $includeProgress = true)
2880
    {
2881
 
2882
        $serviceDatetimeFormat = $this->config['leaderslinked.services.datetime'];
2883
 
2884
        $data = [
2885
            'userlog'   => [],
2886
            'progress'  => [],
2887
            'topics'    => [],
2888
            'quizzes'   => [],
2889
        ];
2890
 
2891
 
2892
        $companies = [];
2893
        $companyMapper = CompanyMapper::getInstance($this->adapter);
2894
 
2895
        $topics = [];
2896
        $topicMapper = CompanyMicrolearningTopicMapper::getInstance($this->adapter);
2897
 
2898
        $capsules = [];
2899
        $capsuleMapper = CompanyMicrolearningCapsuleMapper::getInstance($this->adapter);
2900
 
2901
        $slides = [];
2902
        $slideMapper = CompanyMicrolearningSlideMapper::getInstance($this->adapter);
2903
 
2904
        $quizzes = [];
2905
        $quizMapper = CompanyMicrolearningQuizMapper::getInstance($this->adapter);
2906
 
2907
        $questions = [];
2908
        $questionMapper = CompanyMicrolearningQuestionMapper::getInstance($this->adapter);
2909
 
2910
        $answers = [];
2911
        $answerMapper = CompanyMicrolearningAnswerMapper::getInstance($this->adapter);
2912
 
2913
 
2914
        $userLogMapper = CompanyMicrolearningUserLogMapper::getInstance($this->adapter);
2915
 
2916
        if($includeLogs) {
2917
 
2918
            $records = $userLogMapper->fetchLast20ByUserId($user->id);
2919
            foreach($records as $record)
2920
            {
2921
                $dt = \DateTime::createFromFormat('Y-m-d H:i:s', $record->added_on);
2922
 
2923
                if($record->company_id) {
2924
 
2925
                    if(isset($companies[$record->company_id])) {
2926
                        $company = $companies[$record->company_id];
2927
                    } else {
2928
                        $company = $companyMapper->fetchOne($record->company_id);
2929
                        $companies[$record->company_id] = $company;
2930
                    }
2931
                } else {
2932
                    $company = null;
2933
                }
2934
 
2935
                if($record->topic_id) {
2936
 
2937
                    if(isset($topics[$record->topic_id])) {
2938
                        $topic = $topics[$record->topic_id];
2939
                    } else {
2940
                        $topic = $topicMapper->fetchOne($record->topic_id);
2941
                        $topics[$record->topic_id] = $topic;
2942
                    }
2943
                } else {
2944
                    $topic = null;
2945
                }
2946
 
2947
 
2948
                if($record->capsule_id) {
2949
 
2950
                    if(isset($capsules[$record->capsule_id])) {
2951
                        $capsule = $capsules[$record->capsule_id];
2952
                    } else {
2953
                        $capsule = $capsuleMapper->fetchOne($record->capsule_id);
2954
                        $capsules[$record->capsule_id] = $capsule;
2955
                    }
2956
                } else {
2957
                    $capsule = null;
2958
                }
2959
 
2960
 
2961
                if($record->slide_id) {
2962
 
2963
                    if(isset($slides[$record->slide_id])) {
2964
                        $slide = $slides[$record->slide_id];
2965
                    } else {
2966
                        $slide = $slideMapper->fetchOne($record->slide_id);
2967
                        $slides[$record->slide_id] = $slide;
2968
                    }
2969
                } else {
2970
                    $slide = null;
2971
                }
2972
 
2973
 
2974
                array_push($data['userlog'], [
2975
                    'user_uuid'     => $user->uuid,
2976
                    'company_uuid'  => $company ? $company->uuid : '',
2977
                    'topic_uuid'    => $topic ? $topic->uuid : '',
2978
                    'capsule_uuid'  => $capsule ? $capsule->uuid : '',
2979
                    'slide_uuid'    => $slide ? $slide->uuid : '',
2980
                    'activity'      => $record->activity,
2981
                    'added_on'      => $dt->format($serviceDatetimeFormat),
2982
                ]);
2983
 
2984
 
2985
            }
2986
        }
2987
 
2988
        if($includeProgress) {
2989
 
2990
            $userProgressMapper = CompanyMicrolearningUserProgressMapper::getInstance($this->adapter);
2991
            $records = $userProgressMapper->fetchAllByUserId($user->id);
2992
            foreach($records as $record)
2993
            {
2994
                if($record->company_id) {
2995
 
2996
                    if(isset($companies[$record->company_id])) {
2997
                        $company = $companies[$record->company_id];
2998
                    } else {
2999
                        $company = $companyMapper->fetchOne($record->company_id);
3000
                        $companies[$record->company_id] = $company;
3001
                    }
3002
                } else {
3003
                    $company = null;
3004
                }
3005
 
3006
                if($record->topic_id) {
3007
 
3008
                    if(isset($topics[$record->topic_id])) {
3009
                        $topic = $topics[$record->topic_id];
3010
                    } else {
3011
                        $topic = $topicMapper->fetchOne($record->topic_id);
3012
                        $topics[$record->topic_id] = $topic;
3013
                    }
3014
                } else {
3015
                    $topic = null;
3016
                }
3017
 
3018
 
3019
                if($record->capsule_id) {
3020
 
3021
                    if(isset($capsules[$record->capsule_id])) {
3022
                        $capsule = $capsules[$record->capsule_id];
3023
                    } else {
3024
                        $capsule = $capsuleMapper->fetchOne($record->capsule_id);
3025
                        $capsules[$record->capsule_id] = $capsule;
3026
                    }
3027
                } else {
3028
                    $capsule = null;
3029
                }
3030
 
3031
 
3032
                if($record->slide_id) {
3033
 
3034
                    if(isset($slides[$record->slide_id])) {
3035
                        $slide = $slides[$record->slide_id];
3036
                    } else {
3037
                        $slide = $slideMapper->fetchOne($record->slide_id);
3038
                        $slides[$record->slide_id] = $slide;
3039
                    }
3040
                } else {
3041
                    $slide = null;
3042
                }
3043
 
3044
 
3045
                $dtAddedOn = \DateTime::createFromFormat('Y-m-d H:i:s', $record->added_on);
3046
                $dtUpdatedOn = \DateTime::createFromFormat('Y-m-d H:i:s', $record->updated_on);
3047
 
3048
                array_push($data['progress'], [
3049
                    'user_uuid'                 => $user->uuid,
3050
                    'company_uuid'              => $company ? $company->uuid : '',
3051
                    'topic_uuid'                => $topic ? $topic->uuid : '',
3052
                    'capsule_uuid'              => $capsule ? $capsule->uuid : '',
3053
                    'slide_uuid'                => $slide ? $slide->uuid : '',
3054
                    'progress'                  => $record->progress ? $record->progress : 0,
3055
                    'total_slides'              => $record->total_slides ? $record->total_slides : 0,
3056
                    'view_slides'               => $record->view_slides ? $record->view_slides : 0,
3057
                    'type'                      => $record->type,
3058
                    'returning'                 => $record->returning ? $record->returning : 0,
3059
                    'returning_after_completed' => $record->returning_after_completed ? $record->returning_after_completed : 0,
3060
                    'completed'                 => $record->completed ? $record->completed : 0,
3061
                    'added_on'                  => $dtAddedOn->format($serviceDatetimeFormat),
3062
                    'updated_on'                => $dtUpdatedOn->format($serviceDatetimeFormat),
3063
                ]);
3064
            }
3065
        }
3066
 
3067
 
3068
        $now = date('Y-m-d H:i:s');
3069
        $companies_with_access  = [];
3070
        $topics_with_access     = [];
3071
        $capsules_with_access   = [];
3072
        $quizzes_with_access    = [];
3073
        $quizzes                = [];
3074
 
3075
 
3076
        $capsuleUserMapper = CompanyMicrolearningCapsuleUserMapper::getInstance($this->adapter);
3077
        $records = $capsuleUserMapper->fetchAllActiveByUserId($user->id);
3078
 
3079
 
3080
        foreach($records as $record)
3081
        {
3082
            if($record->access != CompanyMicrolearningCapsuleUser::ACCESS_UNLIMITED && $record->access != CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD) {
3083
                continue;
3084
            }
3085
            if($record->access == CompanyMicrolearningCapsuleUser::ACCESS_PAY_PERIOD) {
3086
                if($now < $record->paid_from || $now > $record->paid_to) {
3087
                    continue;
3088
                }
3089
            }
3090
 
3091
 
3092
            if(!in_array($record->company_id,$companies_with_access)) {
3093
                array_push($companies_with_access, $record->company_id);
3094
            }
3095
 
3096
            if(!in_array($record->topic_id,$topics_with_access)) {
3097
                array_push($topics_with_access, $record->topic_id);
3098
            }
3099
 
3100
            if(!in_array($record->capsule_id,$capsules_with_access)) {
3101
                array_push($capsules_with_access, $record->capsule_id);
3102
            }
3103
        }
3104
 
3105
 /*
3106
        echo '$companies_with_access ' . PHP_EOL;
3107
        print_r($companies_with_access);
3108
 
3109
        echo '$topics_with_access ' . PHP_EOL;
3110
        print_r($topics_with_access);
3111
 
3112
        echo '$capsules_with_access' . PHP_EOL;
3113
        print_r($capsules_with_access);
3114
        */
3115
 
3116
        $companyServiceMapper = CompanyServiceMapper::getInstance($this->adapter);
3117
        foreach($companies_with_access as $company_id)
3118
        {
3119
            $companyService =  $companyServiceMapper->fetchOneActiveByCompanyIdAndServiceId($company_id, Service::MICRO_LEARNING);
3120
 
3121
            //print_r($companyService); exit;
3122
 
3123
            if(!$companyService) {
3124
                continue;
3125
            }
3126
 
3127
 
3128
            if(isset($companies[$companyService->company_id])) {
3129
                $company = $companies[$companyService->company_id];
3130
            } else {
3131
                $company = $companyMapper->fetchOne($companyService->company_id);
3132
                $companies[$companyService->company_id] = $company;
3133
            }
3134
 
3135
            $topics = $topicMapper->fetchAllActiveByCompanyId($company_id);
3136
            foreach($topics as $topic)
3137
            {
3138
                if(!in_array($topic->id, $topics_with_access)) {
3139
                    continue;
3140
                }
3141
 
3142
                $record_capsules = [];
3143
                $capsules = $capsuleMapper->fetchAllActiveByCompanyIdAndTopicId($topic->company_id, $topic->id);
3144
                foreach($capsules as $capsule)
3145
                {
3146
                    if(!in_array($capsule->id, $capsules_with_access)) {
3147
                        continue;
3148
                    }
3149
 
3150
 
3151
                    $record_slides = [];
3152
                    $slides = $slideMapper->fetchAllByCompanyIdAndTopicIdAndCapsuleId($capsule->company_id, $capsule->topic_id, $capsule->id);
3153
                    foreach($slides as $slide)
3154
                    {
3155
                        if($slide->type == CompanyMicrolearningSlide::TYPE_QUIZ) {
3156
                            if(!in_array($slide->quiz_id, $quizzes_with_access)) {
3157
                                array_push($quizzes_with_access, $slide->quiz_id);
3158
                            }
3159
 
3160
                            if(isset($quizzes[$slide->quiz_id])) {
3161
                                $quiz = $quizzes[$slide->quiz_id];
3162
 
3163
                            } else {
3164
                                $quiz = $quizMapper->fetchOne($slide->quiz_id);
3165
                                $quizzes[$slide->quiz_id] =  $quiz;
3166
                            }
3167
                        } else {
3168
                            $quiz = null;
3169
                        }
3170
 
3171
 
3172
 
3173
                        array_push($record_slides, [
3174
                            'uuid' => $slide->uuid,
3175
                            'quiz_uuid' => $quiz ? $quiz->uuid : '',
3176
                            'name' => $slide->name ? $slide->name : '',
3177
                            'description' => $slide->description ? $slide->description : '',
3178
                            'position' => $slide->order,
3179
                            'type' => $slide->type,
3180
                            'background' => $slide->background ? $this->url()->fromRoute('services/storage',['type' => 'microlearning-slide', 'code' => $slide->uuid, 'filename' => $slide->background], ['force_canonical' => true]) : '',
3181
                            'file' => $slide->file ? $this->url()->fromRoute('services/storage',['type' => 'microlearning-slide', 'code' => $slide->uuid, 'filename' => $slide->file], ['force_canonical' => true]) : '',
3182
                        ]);
3183
                    }
3184
 
3185
                    array_push($record_capsules, [
3186
                        'uuid' => $capsule->uuid,
3187
                        'name' => $capsule->name ? $capsule->name : '',
3188
                        'description' => $capsule->description ? $capsule->description : '',
3189
                        'image' => $capsule->image ? $this->url()->fromRoute('services/storage',['type' => 'microlearning-capsule', 'code' => $capsule->uuid, 'filename' => $capsule->image ], ['force_canonical' => true])  : '',
3190
                        'position' => $capsule->order,
3191
                        'slides' => $record_slides,
3192
                    ]);
3193
                }
3194
 
3195
                array_push($data['topics'], [
3196
                    'uuid' => $topic->uuid,
3197
                    'name' => $topic->name ? $topic->name : '',
3198
                    'description' => $topic->description ? $topic->description : '',
3199
                    'image' => $topic->image ? $this->url()->fromRoute('services/storage',['type' => 'microlearning-topic', 'code' => $topic->uuid, 'filename' => $topic->image ], ['force_canonical' => true]) : '',
3200
                    'position' => $topic->order,
3201
                    'company_uuid' => $company->uuid,
3202
                    'company_name' => $company->name,
3203
                    'company_image' => $this->url()->fromRoute('services/storage',['type' => 'company', 'code' => $company->uuid, 'filename' => $company->image], ['force_canonical' => true]),
3204
                    'capsules' => $record_capsules
3205
                ]);
3206
            }
3207
        }
3208
 
3209
 
3210
 
3211
        foreach($quizzes_with_access as $quiz_id)
3212
        {
3213
            if(isset($quizzes[$quiz_id])) {
3214
                $quiz = $quizzes[$quiz_id];
3215
            } else {
3216
                $quiz = $quizMapper->fetchOne($quiz_id);
3217
                array_push($quizzes, $quiz);
3218
            }
3219
 
3220
            if(isset($companies[$quiz->company_id])) {
3221
                $company = $companies[$quiz->company_id];
3222
            } else {
3223
                $company = $companyMapper->fetchOne($quiz->company_id);
3224
                $companies[$quiz->company_id] = $company;
3225
            }
3226
 
3227
 
3228
            $record_questions = [];
3229
            $questions = $questionMapper->fetchAllByQuizId($quiz->id);
3230
            foreach($questions as $question)
3231
            {
3232
                $record_answers = [];
3233
 
3234
                $answers = $answerMapper->fetchAllByQuizIdAndQuestionId($question->quiz_id, $question->id);
3235
                foreach($answers as $answer)
3236
                {
3237
                    array_push($record_answers, [
3238
                        'uuid' => $answer->uuid,
3239
                        'text' => trim($answer->text),
3240
                        'correct' => $answer->correct ? $answer->correct  : 0 ,
3241
                        'points' => intval($answer->points, 10),
3242
                    ]);
3243
                }
3244
 
3245
                array_push($record_questions, [
3246
                    'uuid' => $question->uuid,
3247
                    'text' => trim($question->text),
3248
                    'type' => $question->type,
3249
                    'maxlength' => $question->maxlength,
3250
                    'points' => $question->points,
3251
                    'answers' => $record_answers,
3252
                ]);
3253
            }
3254
 
3255
 
3256
            array_push($data['quizzes'], [
3257
                'uuid' => $quiz->uuid,
3258
                'name' => $quiz->name,
3259
                'text' => trim($quiz->text ? $quiz->text : ''),
3260
                'failed' => trim($quiz->failed ? $quiz->failed : ''),
3261
                'points' => $quiz->points,
3262
                'minimum_points_required' => $quiz->minimum_points_required,
3263
                'max_time' => $quiz->max_time ? $quiz->max_time : 5,
3264
                'company_uuid' => $company->uuid,
3265
                'company_name' => $company->name,
3266
                'company_image' => $this->url()->fromRoute('services/storage',['type' => 'company', 'code' => $company->uuid, 'filename' => $company->image], ['force_canonical' => true]),
3267
                'questions' => $record_questions,
3268
            ]);
3269
        }
3270
        return $data;
3271
    }
3272
 
3273
 
3274
    /**
3275
     *
3276
     * @param string $filename
3277
     * @param boolean $retbytes
3278
     * @return boolean|number
3279
     */
3280
    private function readfile_chunked($filename, $retbytes = true) {
3281
        $buffer = '';
3282
        $cnt =0;;
3283
        $handle = fopen($filename,'rb');
3284
        if ($handle === false) {
3285
            return false;
3286
        }
3287
        while (!feof($handle)) {
3288
            $buffer = fread($handle, self::CHUNK_SIZE);
3289
            echo $buffer;
3290
            ob_flush();
3291
            flush();
3292
            if ($retbytes) {
3293
                $cnt += strlen($buffer);
3294
            }
3295
        }
3296
        $status = fclose($handle);
3297
        if ($retbytes && $status) {
3298
            return $cnt; // return num. bytes delivered like readfile() does.
3299
        }
3300
        return $status;
3301
    }
3302
}