Completed
Push — master ( f27c8b...b35943 )
by greg
06:40 queued 03:40
created

Game::sendShareMail()   D

Complexity

Conditions 11
Paths 126

Size

Total Lines 82
Code Lines 59

Duplication

Lines 0
Ratio 0 %

Importance

Changes 6
Bugs 1 Features 0
Metric Value
c 6
b 1
f 0
dl 0
loc 82
rs 4.963
cc 11
eloc 59
nc 126
nop 7

How to fix   Long Method    Complexity   

Long Method

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

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

Commonly applied refactorings include:

1
<?php
2
namespace PlaygroundGame\Service;
3
4
use PlaygroundGame\Entity\Entry;
5
use Zend\Session\Container;
6
use Zend\ServiceManager\ServiceManagerAwareInterface;
7
use Zend\ServiceManager\ServiceManager;
8
use ZfcBase\EventManager\EventProvider;
9
use PlaygroundGame\Options\ModuleOptions;
10
use PlaygroundGame\Mapper\GameInterface as GameMapperInterface;
11
use DoctrineModule\Validator\NoObjectExists as NoObjectExistsValidator;
12
use Zend\Validator\File\Size;
13
use Zend\Validator\File\IsImage;
14
use Zend\Stdlib\ErrorHandler;
15
use PlaygroundCore\Filter\Sanitize;
16
use Zend\Form\Element;
17
use Zend\Form\Form;
18
use Zend\InputFilter\Factory as InputFactory;
19
20
class Game extends EventProvider implements ServiceManagerAwareInterface
21
{
22
    /**
23
     *
24
     * @var GameMapperInterface
25
     */
26
    protected $gameMapper;
27
28
    /**
29
     *
30
     * @var EntryMapperInterface
31
     */
32
    protected $entryMapper;
33
34
    /**
35
     *
36
     * @var ServiceManager
37
     */
38
    protected $serviceManager;
39
40
    /**
41
     *
42
     * @var UserServiceOptionsInterface
43
     */
44
    protected $options;
45
46
    protected $playerformMapper;
47
48
    protected $invitationMapper;
49
    
50
    protected $anonymousIdentifier = null;
51
52
    /**
53
     *
54
     *
55
     * This service is ready for all types of games
56
     *
57
     * @param array $data
58
     * @param string $formClass
59
     * @return \PlaygroundGame\Entity\Game
60
     */
61
    public function createOrUpdate(array $data, $game, $formClass)
62
    {
63
        $entityManager = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
64
65
        $form = $this->getServiceManager()->get($formClass);
66
        $form->get('publicationDate')->setOptions(array(
67
            'format' => 'Y-m-d'
68
        ));
69
        $form->get('startDate')->setOptions(array(
70
            'format' => 'Y-m-d'
71
        ));
72
        $form->get('endDate')->setOptions(array(
73
            'format' => 'Y-m-d'
74
        ));
75
        $form->get('closeDate')->setOptions(array(
76
            'format' => 'Y-m-d'
77
        ));
78
79
        $form->bind($game);
80
81
        $path = $this->getOptions()->getMediaPath() . '/';
82
        $media_url = $this->getOptions()->getMediaUrl() . '/';
83
84
        $identifierInput = $form->getInputFilter()->get('identifier');
85
        $noObjectExistsValidator = new NoObjectExistsValidator(array(
86
            'object_repository' => $entityManager->getRepository('PlaygroundGame\Entity\Game'),
87
            'fields' => 'identifier',
88
            'messages' => array(
89
                'objectFound' => 'This url already exists !'
90
            )
91
        ));
92
93
        if ($game->getIdentifier() != $data['identifier']) {
94
            $identifierInput->getValidatorChain()->addValidator($noObjectExistsValidator);
95
        }
96
97
        // I must switch from original format to the Y-m-d format because
98
        // this is the only one accepted by new DateTime($value)
99 View Code Duplication
        if (isset($data['publicationDate']) && $data['publicationDate']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
100
            $tmpDate = \DateTime::createFromFormat('d/m/Y', $data['publicationDate']);
101
            $data['publicationDate'] = $tmpDate->format('Y-m-d');
102
        }
103 View Code Duplication
        if (isset($data['startDate']) && $data['startDate']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
104
            $tmpDate = \DateTime::createFromFormat('d/m/Y', $data['startDate']);
105
            $data['startDate'] = $tmpDate->format('Y-m-d');
106
        }
107 View Code Duplication
        if (isset($data['endDate']) && $data['endDate']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
108
            $tmpDate = \DateTime::createFromFormat('d/m/Y', $data['endDate']);
109
            $data['endDate'] = $tmpDate->format('Y-m-d');
110
        }
111 View Code Duplication
        if (isset($data['closeDate']) && $data['closeDate']) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
112
            $tmpDate = \DateTime::createFromFormat('d/m/Y', $data['closeDate']);
113
            $data['closeDate'] = $tmpDate->format('Y-m-d');
114
        }
115
116
        // If publicationDate is null, I update it with the startDate if not null neither
117
        if ((! isset($data['publicationDate']) || $data['publicationDate'] == '') &&
118
            (isset($data['startDate']) && $data['startDate'] != '')
119
        ) {
120
            $data['publicationDate'] = $data['startDate'];
121
        }
122
123
        // If the identifier has not been set, I use the title to create one.
124 View Code Duplication
        if ((! isset($data['identifier']) || empty($data['identifier'])) && isset($data['title'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
125
            $data['identifier'] = $data['title'];
126
        }
127
128
        $form->setData($data);
129
130
        // If someone want to claim... It's time to do it ! used for exemple by PlaygroundFacebook Module
131
        $result = $this->getEventManager()->trigger(__FUNCTION__ . '.validate', $this, array(
132
            'game' => $game,
133
            'data' => $data
134
        ));
135
        if (is_array($result) && ! $result[0]) {
136
            $form->get('fbAppId')->setMessages(array(
137
                'Vous devez d\'abord désinstaller l\'appli Facebook'
138
            ));
139
140
            return false;
0 ignored issues
show
Bug Best Practice introduced by
The return type of return false; (false) is incompatible with the return type documented by PlaygroundGame\Service\Game::createOrUpdate of type PlaygroundGame\Entity\Game.

If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.

Let’s take a look at an example:

class Author {
    private $name;

    public function __construct($name) {
        $this->name = $name;
    }

    public function getName() {
        return $this->name;
    }
}

abstract class Post {
    public function getAuthor() {
        return 'Johannes';
    }
}

class BlogPost extends Post {
    public function getAuthor() {
        return new Author('Johannes');
    }
}

class ForumPost extends Post { /* ... */ }

function my_function(Post $post) {
    echo strtoupper($post->getAuthor());
}

Our function my_function expects a Post object, and outputs the author of the post. The base class Post returns a simple string and outputting a simple string will work just fine. However, the child class BlogPost which is a sub-type of Post instead decided to return an object, and is therefore violating the SOLID principles. If a BlogPost were passed to my_function, PHP would not complain, but ultimately fail when executing the strtoupper call in its body.

Loading history...
141
        }
142
143
        if (! $form->isValid()) {
144
            if (isset($data['publicationDate']) && $data['publicationDate']) {
145
                $tmpDate = \DateTime::createFromFormat('Y-m-d', $data['publicationDate']);
146
                $data['publicationDate'] = $tmpDate->format('d/m/Y');
147
                $form->setData(array(
148
                    'publicationDate' => $data['publicationDate']
149
                ));
150
            }
151
            if (isset($data['startDate']) && $data['startDate']) {
152
                $tmpDate = \DateTime::createFromFormat('Y-m-d', $data['startDate']);
153
                $data['startDate'] = $tmpDate->format('d/m/Y');
154
                $form->setData(array(
155
                    'startDate' => $data['startDate']
156
                ));
157
            }
158
            if (isset($data['endDate']) && $data['endDate']) {
159
                $tmpDate = \DateTime::createFromFormat('Y-m-d', $data['endDate']);
160
                $data['endDate'] = $tmpDate->format('d/m/Y');
161
                $form->setData(array(
162
                    'endDate' => $data['endDate']
163
                ));
164
            }
165
            if (isset($data['closeDate']) && $data['closeDate']) {
166
                $tmpDate = \DateTime::createFromFormat('Y-m-d', $data['closeDate']);
167
                $data['closeDate'] = $tmpDate->format('d/m/Y');
168
                $form->setData(array(
169
                    'closeDate' => $data['closeDate']
170
                ));
171
            }
172
            return false;
0 ignored issues
show
Bug Best Practice introduced by
The return type of return false; (false) is incompatible with the return type documented by PlaygroundGame\Service\Game::createOrUpdate of type PlaygroundGame\Entity\Game.

If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.

Let’s take a look at an example:

class Author {
    private $name;

    public function __construct($name) {
        $this->name = $name;
    }

    public function getName() {
        return $this->name;
    }
}

abstract class Post {
    public function getAuthor() {
        return 'Johannes';
    }
}

class BlogPost extends Post {
    public function getAuthor() {
        return new Author('Johannes');
    }
}

class ForumPost extends Post { /* ... */ }

function my_function(Post $post) {
    echo strtoupper($post->getAuthor());
}

Our function my_function expects a Post object, and outputs the author of the post. The base class Post returns a simple string and outputting a simple string will work just fine. However, the child class BlogPost which is a sub-type of Post instead decided to return an object, and is therefore violating the SOLID principles. If a BlogPost were passed to my_function, PHP would not complain, but ultimately fail when executing the strtoupper call in its body.

Loading history...
173
        }
174
175
        $game = $form->getData();
176
        $game = $this->getGameMapper()->insert($game);
177
178
        // I wait for the game to be saved to obtain its ID.
179 View Code Duplication
        if (! empty($data['uploadMainImage']['tmp_name'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
180
            ErrorHandler::start();
181
            $data['uploadMainImage']['name'] = $this->fileNewname(
182
                $path,
183
                $game->getId() . "-" . $data['uploadMainImage']['name']
184
            );
185
            move_uploaded_file($data['uploadMainImage']['tmp_name'], $path . $data['uploadMainImage']['name']);
186
            $game->setMainImage($media_url . $data['uploadMainImage']['name']);
187
            ErrorHandler::stop(true);
188
        }
189
190 View Code Duplication
        if (isset($data['deleteMainImage']) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
191
            $data['deleteMainImage'] &&
192
            empty($data['uploadMainImage']['tmp_name'])
193
        ) {
194
            ErrorHandler::start();
195
            $image = $game->getMainImage();
196
            $image = str_replace($media_url, '', $image);
197
            unlink($path . $image);
198
            $game->setMainImage(null);
199
            ErrorHandler::stop(true);
200
        }
201
202 View Code Duplication
        if (! empty($data['uploadSecondImage']['tmp_name'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
203
            ErrorHandler::start();
204
            $data['uploadSecondImage']['name'] = $this->fileNewname(
205
                $path,
206
                $game->getId() . "-" . $data['uploadSecondImage']['name']
207
            );
208
            move_uploaded_file($data['uploadSecondImage']['tmp_name'], $path . $data['uploadSecondImage']['name']);
209
            $game->setSecondImage($media_url . $data['uploadSecondImage']['name']);
210
            ErrorHandler::stop(true);
211
        }
212
213 View Code Duplication
        if (isset($data['deleteSecondImage']) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
214
            $data['deleteSecondImage'] &&
215
            empty($data['uploadSecondImage']['tmp_name'])
216
        ) {
217
            ErrorHandler::start();
218
            $image = $game->getSecondImage();
219
            $image = str_replace($media_url, '', $image);
220
            unlink($path . $image);
221
            $game->setSecondImage(null);
222
            ErrorHandler::stop(true);
223
        }
224
225
        if (! empty($data['uploadStylesheet']['tmp_name'])) {
226
            ErrorHandler::start();
227
            move_uploaded_file($data['uploadStylesheet']['tmp_name'], $path . 'stylesheet_' . $game->getId() . '.css');
228
            $game->setStylesheet($media_url . 'stylesheet_' . $game->getId() . '.css');
229
            ErrorHandler::stop(true);
230
        }
231
232 View Code Duplication
        if (! empty($data['uploadFbShareImage']['tmp_name'])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
233
            ErrorHandler::start();
234
            $data['uploadFbShareImage']['name'] = $this->fileNewname(
235
                $path,
236
                $game->getId() . "-" . $data['uploadFbShareImage']['name']
237
            );
238
            move_uploaded_file($data['uploadFbShareImage']['tmp_name'], $path . $data['uploadFbShareImage']['name']);
239
            $game->setFbShareImage($media_url . $data['uploadFbShareImage']['name']);
240
            ErrorHandler::stop(true);
241
        }
242
243 View Code Duplication
        if (isset($data['deleteFbShareImage']) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
244
            $data['deleteFbShareImage'] &&
245
            empty($data['uploadFbShareImage']['tmp_name'])
246
        ) {
247
            ErrorHandler::start();
248
            $image = $game->getFbShareImage();
249
            $image = str_replace($media_url, '', $image);
250
            unlink($path . $image);
251
            $game->setFbShareImage(null);
252
            ErrorHandler::stop(true);
253
        }
254
255
        if (! empty($data['uploadFbPageTabImage']['tmp_name'])) {
256
            ErrorHandler::start();
257
            $extension = $this->getExtension(strtolower($data['uploadFbPageTabImage']['name']));
258
            $src = $this->getSrc($extension, $data['uploadFbPageTabImage']['tmp_name']);
259
            $this->resize(
260
                $data['uploadFbPageTabImage']['tmp_name'],
261
                $extension,
262
                $path . $game->getId() . "-" . $data['uploadFbPageTabImage']['name'],
263
                $src,
264
                111,
265
                74
266
            );
267
268
            $game->setFbPageTabImage($media_url . $game->getId() . "-" . $data['uploadFbPageTabImage']['name']);
269
            ErrorHandler::stop(true);
270
        }
271
272 View Code Duplication
        if (isset($data['deleteFbPageTabImage']) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
273
            $data['deleteFbPageTabImage'] &&
274
            empty($data['uploadFbPageTabImage']['tmp_name'])
275
        ) {
276
            ErrorHandler::start();
277
            $image = $game->getFbPageTabImage();
278
            $image = str_replace($media_url, '', $image);
279
            unlink($path . $image);
280
            $game->setFbPageTabImage(null);
281
            ErrorHandler::stop(true);
282
        }
283
284
        $game = $this->getGameMapper()->update($game);
285
286
        $prize_mapper = $this->getServiceManager()->get('playgroundgame_prize_mapper');
287
        if (isset($data['prizes'])) {
288
            foreach ($data['prizes'] as $prize_data) {
289
                if (! empty($prize_data['picture_file']['tmp_name']) && ! $prize_data['picture_file']['error']) {
290
                    if ($prize_data['id']) {
291
                        $prize = $prize_mapper->findById($prize_data['id']);
292
                    } else {
293
                        $some_prizes = $prize_mapper->findBy(array(
294
                            'game' => $game,
295
                            'title' => $prize_data['title']
296
                        ));
297
                        if (count($some_prizes) == 1) {
298
                            $prize = $some_prizes[0];
299
                        } else {
300
                            return false;
0 ignored issues
show
Bug Best Practice introduced by
The return type of return false; (false) is incompatible with the return type documented by PlaygroundGame\Service\Game::createOrUpdate of type PlaygroundGame\Entity\Game.

If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.

Let’s take a look at an example:

class Author {
    private $name;

    public function __construct($name) {
        $this->name = $name;
    }

    public function getName() {
        return $this->name;
    }
}

abstract class Post {
    public function getAuthor() {
        return 'Johannes';
    }
}

class BlogPost extends Post {
    public function getAuthor() {
        return new Author('Johannes');
    }
}

class ForumPost extends Post { /* ... */ }

function my_function(Post $post) {
    echo strtoupper($post->getAuthor());
}

Our function my_function expects a Post object, and outputs the author of the post. The base class Post returns a simple string and outputting a simple string will work just fine. However, the child class BlogPost which is a sub-type of Post instead decided to return an object, and is therefore violating the SOLID principles. If a BlogPost were passed to my_function, PHP would not complain, but ultimately fail when executing the strtoupper call in its body.

Loading history...
301
                        }
302
                    }
303
                    // Remove if existing image
304
                    if ($prize->getPicture() && file_exists($prize->getPicture())) {
305
                        unlink($prize->getPicture());
306
                        $prize->getPicture(null);
307
                    }
308
                    // Upload and set new
309
                    ErrorHandler::start();
310
                    $filename = "game-" . $game->getId() . "-prize-";
311
                    $filename .= $prize->getId() . "-" . $prize_data['picture_file']['name'];
312
                    move_uploaded_file($prize_data['picture_file']['tmp_name'], $path . $filename);
313
                    $prize->setPicture($media_url . $filename);
314
                    ErrorHandler::stop(true);
315
                    $prize_mapper->update($prize);
316
                }
317
            }
318
        }
319
        // If I receive false, it means that the FB Id was not available anymore
320
        $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
321
            'game' => $game
322
        ));
323
324
        return $game;
325
    }
326
    
327
    /**
328
     * getActiveGames
329
     *
330
     * @return Array of PlaygroundGame\Entity\Game
331
     */
332
    public function getActiveGames($displayHome = true, $classType = '', $order = '')
333
    {
334
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
335
        $today = new \DateTime("now");
336
        $today = $today->format('Y-m-d') . ' 23:59:59';
337
        $orderBy = 'g.publicationDate';
338
        if ($order != '') {
339
            $orderBy = 'g.'.$order;
340
        }
341
342
        $qb = $em->createQueryBuilder();
343
        $and = $qb->expr()->andx();
344
        $and->add(
345
            $qb->expr()->orX(
346
                $qb->expr()->lte('g.publicationDate', ':date'),
347
                $qb->expr()->isNull('g.publicationDate')
348
            )
349
        );
350
        $and->add(
351
            $qb->expr()->orX(
352
                $qb->expr()->gte('g.closeDate', ':date'),
353
                $qb->expr()->isNull('g.closeDate')
354
            )
355
        );
356
        $qb->setParameter('date', $today);
357
        
358
        $and->add($qb->expr()->eq('g.active', '1'));
359
        $and->add($qb->expr()->eq('g.broadcastPlatform', '1'));
360
        
361
        if ($classType != '') {
362
            $and->add($qb->expr()->eq('g.classType', ':classType'));
363
            $qb->setParameter('classType', $classType);
364
        }
365
        
366
        if ($displayHome) {
367
            $and->add($qb->expr()->eq('g.displayHome', true));
368
        }
369
        
370
        $qb->select('g')
371
        ->from('PlaygroundGame\Entity\Game', 'g')
372
        ->where($and)
373
        ->orderBy($orderBy, 'DESC');
374
        
375
        $query = $qb->getQuery();
376
        $games = $query->getResult();
377
        
378
        // je les classe par date de publication (date comme clé dans le tableau afin de pouvoir merger les objets
379
        // de type article avec le même procédé en les classant naturellement par date asc ou desc
380
        $arrayGames = array();
381 View Code Duplication
        foreach ($games as $game) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
382
            if ($game->getPublicationDate()) {
383
                $key = $game->getPublicationDate()->format('Ymd');
384
            } elseif ($game->getStartDate()) {
385
                $key = $game->getStartDate()->format('Ymd');
386
            } else {
387
                $key = $game->getUpdatedAt()->format('Ymd');
388
            }
389
            $key .= $game->getUpdatedAt()->format('Ymd') . '-' . $game->getId();
390
            $arrayGames[$key] = $game;
391
        }
392
393
        return $arrayGames;
394
    }
395
396
    /**
397
     * getAvailableGames : Games OnLine and not already played by $user
398
     *
399
     * @return Array of PlaygroundGame\Entity\Game
400
     */
401
    public function getAvailableGames($user, $maxResults = 2)
402
    {
403
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
404
        $today = new \DateTime("now");
405
        $today = $today->format('Y-m-d') . ' 23:59:59';
406
407
        // Game active with a start_date before today (or without start_date)
408
        // and end_date after today (or without end-date)
409
        $query = $em->createQuery('SELECT g FROM PlaygroundGame\Entity\Game g
410
                WHERE NOT EXISTS (SELECT l FROM PlaygroundGame\Entity\Entry l WHERE l.game = g AND l.user = :user)
411
                AND (g.startDate <= :date OR g.startDate IS NULL)
412
                AND (g.endDate >= :date OR g.endDate IS NULL)
413
                AND g.active = 1 AND g.broadcastPlatform = 1
414
                ORDER BY g.startDate ASC');
415
        $query->setParameter('date', $today);
416
        $query->setParameter('user', $user);
417
        $query->setMaxResults($maxResults);
418
        $games = $query->getResult();
419
420
        return $games;
421
    }
422
423 View Code Duplication
    public function getEntriesQuery($game)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
424
    {
425
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
426
427
        $qb = $em->createQueryBuilder();
428
        $qb->select('
429
            e.id,
430
            u.username,
431
            u.title,
432
            u.firstname,
433
            u.lastname,
434
            u.email,
435
            u.optin,
436
            u.optinPartner,
437
            u.address,
438
            u.address2,
439
            u.postalCode,
440
            u.city,
441
            u.telephone,
442
            u.mobile,
443
            u.created_at,
444
            u.dob,
445
            e.winner,
446
            e.socialShares,
447
            e.playerData,
448
            e.updated_at
449
            ')
450
            ->from('PlaygroundGame\Entity\Entry', 'e')
451
            ->leftJoin('e.user', 'u')
452
            ->where($qb->expr()->eq('e.game', ':game'));
453
        
454
        $qb->setParameter('game', $game);
455
456
        return $qb->getQuery();
457
    }
458
459
    public function getEntriesHeader($game)
460
    {
461
        if ($game->getPlayerForm()) {
462
            $formPV = json_decode($game->getPlayerForm()->getForm(), true);
463
            $header = array('id'=> 1);
464 View Code Duplication
            foreach ($formPV as $element) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
465
                foreach ($element as $k => $v) {
466
                    if ($k !== 'form_properties') {
467
                        $header[$v[0]['name']] = 1;
468
                    }
469
                }
470
            }
471
        } else {
472
            $header = array(
473
                'id' => 1,
474
                'username' => 1,
475
                'title' => 1,
476
                'firstname' => 1,
477
                'lastname' => 1,
478
                'email' => 1,
479
                'optin' => 1,
480
                'optinPartner' => 1,
481
                'address' => 1,
482
                'address2' => 1,
483
                'postalCode' => 1,
484
                'city' => 1,
485
                'telephone' => 1,
486
                'mobile' => 1,
487
                'created_at' => 1,
488
                'dob' => 1,
489
                'winner' => 1
490
            );
491
        }
492
        $header['winner'] = 1;
493
        $header['socialShares'] = 1;
494
        $header['updated_at'] = 1;
495
496
        return $header;
497
    }
498
499
    /**
500
    * getGameEntries : I create an array of entries based on playerData + header
501
    *
502
    * @return Array of PlaygroundGame\Entity\Game
503
    */
504
    public function getGameEntries($header, $entries, $game)
505
    {
506
        $header = $this->getEntriesHeader($game);
507
508
        $results = array();
509
510
        foreach ($entries as $k => $entry) {
511
            $entryData = json_decode($entry['playerData'], true);
512 View Code Duplication
            foreach ($header as $key => $v) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
513
                if (isset($entryData[$key])) {
514
                    $results[$k][$key] = (is_array($entryData[$key]))?implode(', ', $entryData[$key]):$entryData[$key];
515
                } elseif (array_key_exists($key, $entry)) {
516
                    $results[$k][$key] = ($entry[$key] instanceof \DateTime)?
517
                        $entry[$key]->format('Y-m-d'):
518
                        $entry[$key];
519
                } else {
520
                    $results[$k][$key] = '';
521
                }
522
            }
523
        }
524
525
        return $results;
526
    }
527
528
    /**
529
     * getActiveSliderGames
530
     *
531
     * @return Array of PlaygroundGame\Entity\Game
532
     */
533
    public function getActiveSliderGames()
534
    {
535
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
536
        $today = new \DateTime("now");
537
        $today = $today->format('Y-m-d') . ' 23:59:59';
538
539
        // Game active with a start_date before today (or without start_date)
540
        // and end_date after today (or without end-date)
541
        $query = $em->createQuery('SELECT g FROM PlaygroundGame\Entity\Game g
542
            WHERE (g.publicationDate <= :date OR g.publicationDate IS NULL)
543
            AND (g.closeDate >= :date OR g.closeDate IS NULL)
544
            AND g.active = true AND g.broadcastPlatform = 1 AND g.pushHome = true');
545
        $query->setParameter('date', $today);
546
        $games = $query->getResult();
547
548
        // je les classe par date de publication (date comme clé dans le tableau afin de pouvoir merger les objets
549
        // de type article avec le même procédé en les classant naturellement par date asc ou desc
550
        $arrayGames = array();
551 View Code Duplication
        foreach ($games as $game) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
552
            if ($game->getPublicationDate()) {
553
                $key = $game->getPublicationDate()->format('Ymd');
554
            } elseif ($game->getStartDate()) {
555
                $key = $game->getStartDate()->format('Ymd');
556
            } else {
557
                $key = $game->getUpdatedAt()->format('Ymd');
558
            }
559
            $key .= $game->getUpdatedAt()->format('Ymd') . '-' . $game->getId();
560
            $arrayGames[$key] = $game;
561
        }
562
563
        return $arrayGames;
564
    }
565
566
    /**
567
     * getPrizeCategoryGames
568
     *
569
     * @return Array of PlaygroundGame\Entity\Game
570
     */
571 View Code Duplication
    public function getPrizeCategoryGames($categoryid)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
572
    {
573
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
574
575
        $query = $em->createQuery('SELECT g FROM PlaygroundGame\Entity\Game g
576
            WHERE (g.prizeCategory = :categoryid AND g.broadcastPlatform = 1)
577
            ORDER BY g.publicationDate DESC');
578
        $query->setParameter('categoryid', $categoryid);
579
        $games = $query->getResult();
580
581
        return $games;
582
    }
583
584
    public function checkGame($identifier, $checkIfStarted = true)
585
    {
586
        $gameMapper = $this->getGameMapper();
587
588
        if (! $identifier) {
589
            return false;
590
        }
591
592
        $game = $gameMapper->findByIdentifier($identifier);
593
594
        // the game has not been found
595
        if (! $game) {
596
            return false;
597
        }
598
599
        // for preview stuff as admin
600
        if ($this->isAllowed('game', 'edit')) {
601
            $r =$this->getServiceManager()->get('request');
602
            if ($r->getQuery()->get('preview')) {
603
                $game->setActive(true);
604
                $game->setStartDate(null);
605
                $game->setEndDate(null);
606
                $game->setPublicationDate(null);
607
                $game->setBroadcastPlatform(true);
608
609
                // I don't want the game to be updated through any update during the preview mode.
610
                // I mark it as readonly for Doctrine
611
                $this->getServiceManager()
612
                    ->get('doctrine.entitymanager.orm_default')
613
                    ->getUnitOfWork()
614
                    ->markReadOnly($game);
615
                    
616
                return $game;
617
            }
618
        }
619
620
        // The game is inactive
621
        if (! $game->getActive()) {
622
            return false;
623
        }
624
625
        // the game has not begun yet
626
        if (! $game->isOpen()) {
627
            return false;
628
        }
629
630
        // the game is finished and closed
631
        if (! $game->isStarted() && $checkIfStarted) {
632
            return false;
633
        }
634
635
        return $game;
636
    }
637
638
    /**
639
     * Return the last entry of the user on this game, if it exists.
640
     * An entry can be associated to :
641
     * - A user account (a real one, linked to PlaygroundUser
642
     * - An anonymous Identifier (based on one value of playerData (generally email))
643
     * - A cookie set on the player device (the less secure)
644
     * If the active param is set, it can check if the entry is active or not.
645
     * If the bonus param is set, it can check if the entry is a bonus or not.
646
     *
647
     * @param unknown $game
648
     * @param string $user
649
     * @param boolean $active
650
     * @param boolean $bonus
651
     * @return boolean
652
     */
653
    public function checkExistingEntry($game, $user = null, $active = null, $bonus = null)
654
    {
655
        $search = array('game'  => $game);
656
657
        if ($user) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $user of type string|null is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== null instead.

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

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
658
            $search['user'] = $user;
659
        } elseif ($this->getAnonymousIdentifier()) {
660
            $search['anonymousIdentifier'] = $this->getAnonymousIdentifier();
661
            $search['user'] = null;
662
        } else {
663
            $search['anonymousId'] = $this->getAnonymousId();
664
            $search['user'] = null;
665
        }
666
        
667
        if (! is_null($active)) {
668
            $search['active'] = $active;
669
        }
670
        if (! is_null($bonus)) {
671
            $search['bonus'] = $bonus;
672
        }
673
674
        $entry = $this->getEntryMapper()->findOneBy($search, array('updated_at' => 'desc'));
675
676
        return $entry;
677
    }
678
679
    /*
680
    * This function updates the entry with the player data after checking 
681
    * that the data are compliant with the formUser Game attribute
682
    *
683
    * The $data has to be a json object
684
    */
685
    public function updateEntryPlayerForm($data, $game, $user, $entry, $mandatory = true)
0 ignored issues
show
Unused Code introduced by
The parameter $user is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
686
    {
687
        $form = $this->createFormFromJson($game->getPlayerForm()->getForm(), 'playerForm');
688
        $form->setData($data);
689
690
        if (!$mandatory) {
691
            $filter = $form->getInputFilter();
692
            foreach ($form->getElements() as $element) {
693
                try {
694
                    $elementInput = $filter->get($element->getName());
695
                    $elementInput->setRequired(false);
0 ignored issues
show
Bug introduced by
The method setRequired does only exist in Zend\InputFilter\InputInterface, but not in Zend\InputFilter\InputFilterInterface.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
696
                    $form->get($element->getName())->setAttribute('required', false);
697
                } catch (\Zend\Form\Exception\InvalidElementException $e) {
0 ignored issues
show
Coding Style Comprehensibility introduced by
Consider adding a comment why this CATCH block is empty.
Loading history...
698
                }
699
            }
700
        }
701
702
        if ($form->isValid()) {
703
            $dataJson = json_encode($form->getData());
704
705
            if ($game->getAnonymousAllowed() &&
706
                $game->getAnonymousIdentifier() &&
707
                isset($data[$game->getAnonymousIdentifier()])
708
            ) {
709
                $session = new \Zend\Session\Container('anonymous_identifier');
710
                if (empty($session->offsetGet('anonymous_identifier'))) {
711
                    $anonymousIdentifier = $data[$game->getAnonymousIdentifier()];
712
                
713
                    $entry->setAnonymousIdentifier($anonymousIdentifier);
714
                
715
                    // I must transmit this info during the whole game workflow
716
                    $session->offsetSet('anonymous_identifier', $anonymousIdentifier);
717
                }
718
            }
719
720
            $entry->setPlayerData($dataJson);
721
            $this->getEntryMapper()->update($entry);
722
        } else {
723
            return false;
724
        }
725
726
        return true;
727
    }
728
729
730
    public function checkIsFan($game)
0 ignored issues
show
Unused Code introduced by
The parameter $game is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
731
    {
732
        // If on Facebook, check if you have to be a FB fan to play the game
733
        $session = new Container('facebook');
734
735
        if ($session->offsetExists('signed_request')) {
736
            // I'm on Facebook
737
            $sr = $session->offsetGet('signed_request');
738
            if ($sr['page']['liked'] == 1) {
739
                return true;
740
            }
741
        } else {
742
            // I'm not on Facebook
743
            return true;
744
        }
745
746
        return false;
747
    }
748
    
749
    public function getAnonymousIdentifier()
750
    {
751
        if (is_null($this->anonymousIdentifier)) {
752
            // If on Facebook, check if you have to be a FB fan to play the game
753
            $session = new Container('anonymous_identifier');
754
            
755
            if ($session->offsetExists('anonymous_identifier')) {
756
                $this->anonymousIdentifier = $session->offsetGet('anonymous_identifier');
757
            } else {
758
                $this->anonymousIdentifier = false;
759
            }
760
        }
761
    
762
        return $this->anonymousIdentifier;
763
    }
764
765
    /**
766
     * errors :
767
     * -1 : user not connected
768
     * -2 : limit entry games for this user reached
769
     *
770
     * @param \PlaygroundGame\Entity\Game $game
771
     * @param \PlaygroundUser\Entity\UserInterface $user
772
     * @return number unknown
773
     */
774
    public function play($game, $user)
775
    {
776
777
        // certaines participations peuvent rester ouvertes.
778
        // On autorise alors le joueur à reprendre là ou il en était
779
        // par exemple les postvote...
780
        $entry = $this->checkExistingEntry($game, $user, true);
0 ignored issues
show
Documentation introduced by
$user is of type object<PlaygroundUser\Entity\UserInterface>, but the function expects a string|null.

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

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

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

function acceptsInteger($int) { }

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

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
781
782
        if (! $entry) {
783
            if ($this->hasReachedPlayLimit($game, $user)) {
784
                return false;
0 ignored issues
show
Bug Best Practice introduced by
The return type of return false; (false) is incompatible with the return type documented by PlaygroundGame\Service\Game::play of type integer|double.

If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.

Let’s take a look at an example:

class Author {
    private $name;

    public function __construct($name) {
        $this->name = $name;
    }

    public function getName() {
        return $this->name;
    }
}

abstract class Post {
    public function getAuthor() {
        return 'Johannes';
    }
}

class BlogPost extends Post {
    public function getAuthor() {
        return new Author('Johannes');
    }
}

class ForumPost extends Post { /* ... */ }

function my_function(Post $post) {
    echo strtoupper($post->getAuthor());
}

Our function my_function expects a Post object, and outputs the author of the post. The base class Post returns a simple string and outputting a simple string will work just fine. However, the child class BlogPost which is a sub-type of Post instead decided to return an object, and is therefore violating the SOLID principles. If a BlogPost were passed to my_function, PHP would not complain, but ultimately fail when executing the strtoupper call in its body.

Loading history...
785
            }
786
787
            $entry = new Entry();
788
            $entry->setGame($game);
789
            $entry->setUser($user);
790
            $entry->setPoints(0);
791
            $entry->setIp($this->getIp());
792
            $entry->setAnonymousId($this->getAnonymousId());
793
            if ($this->getAnonymousIdentifier()) {
794
                $entry->setAnonymousIdentifier($this->getAnonymousIdentifier());
795
            }
796
797
            $entry = $this->getEntryMapper()->insert($entry);
798
            $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
799
                'user' => $user,
800
                'game' => $game,
801
                'entry' => $entry
802
            ));
803
        }
804
805
        return $entry;
806
    }
807
808
    /**
809
     * @param \PlaygroundGame\Entity\Game $game
810
     * @param \PlaygroundUser\Entity\UserInterface $user
811
     */
812
    public function hasReachedPlayLimit($game, $user)
813
    {
814
        // Is there a limitation on the game ?
815
        $limitAmount = $game->getPlayLimit();
816
        if ($limitAmount) {
817
            $limitScale = $game->getPlayLimitScale();
818
            $userEntries = $this->findLastEntries($game, $user, $limitScale);
819
820
            // player has reached the game limit
821
            if ($userEntries >= $limitAmount) {
822
                return true;
823
            }
824
        }
825
        return false;
826
    }
827
    
828
    /**
829
     * @param \PlaygroundGame\Entity\Game $game
830
     * @param \PlaygroundUser\Entity\UserInterface $user
831
     */
832
    public function findLastEntries($game, $user, $limitScale)
833
    {
834
        $limitDate = $this->getLimitDate($limitScale);
835
836
        if ($user) {
837
            return $this->getEntryMapper()->findLastEntriesByUser($game, $user, $limitDate);
838
        } elseif ($this->getAnonymousIdentifier()) {
839
            return $this->getEntryMapper()->findLastEntriesByAnonymousIdentifier(
840
                $game,
841
                $this->getAnonymousIdentifier(),
842
                $limitDate
843
            );
844
        } else {
845
            return $this->getEntryMapper()->findLastEntriesByIp($game, $this->getIp(), $limitDate);
846
        }
847
    }
848
849
    /**
850
    *
851
    *
852
    */
853
    public function getLimitDate($limitScale)
854
    {
855
        $now = new \DateTime("now");
856
        switch ($limitScale) {
857
            case 'always':
858
                $interval = 'P100Y';
859
                $now->sub(new \DateInterval($interval));
860
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
861
                break;
862
            case 'day':
863
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
864
                break;
865
            case 'week':
866
                $interval = 'P7D';
867
                $now->sub(new \DateInterval($interval));
868
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
869
                break;
870
            case 'month':
871
                $interval = 'P1M';
872
                $now->sub(new \DateInterval($interval));
873
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
874
                break;
875
            case 'year':
876
                $interval = 'P1Y';
877
                $now->sub(new \DateInterval($interval));
878
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
879
                break;
880
            default:
881
                $interval = 'P100Y';
882
                $now->sub(new \DateInterval($interval));
883
                $dateLimit = $now->format('Y-m-d') . ' 0:0:0';
884
        }
885
886
        return $dateLimit;
887
    }
888
889
    public function findLastActiveEntry($game, $user)
890
    {
891
        return $this->checkExistingEntry($game, $user, true);
892
    }
893
894
    public function findLastInactiveEntry($game, $user)
895
    {
896
        return $this->checkExistingEntry($game, $user, false, false);
897
    }
898
899
    public function findLastEntry($game, $user)
900
    {
901
        return $this->checkExistingEntry($game, $user, null, false);
902
    }
903
904
    public function sendShareMail(
905
        $data,
906
        $game,
907
        $user,
908
        $entry,
909
        $template = 'share_game',
910
        $topic = null,
911
        $userTimer = array()
912
    ) {
913
        $mailService = $this->getServiceManager()->get('playgroundgame_message');
914
        $mailSent = false;
915
        $from = $this->getOptions()->getEmailFromAddress();
916
        $subject = $this->getOptions()->getShareSubjectLine();
917
        $renderer = $this->getServiceManager()->get('Zend\View\Renderer\RendererInterface');
918
        if ($user) {
919
            $from = $user->getEmail();
920
        } elseif ($entry && $entry->getAnonymousIdentifier()) {
921
            $from = $entry->getAnonymousIdentifier();
922
        }
923
924
        $skinUrl = $renderer->url(
925
            'frontend',
926
            array(),
927
            array('force_canonical' => true)
928
        );
929
        $secretKey = strtoupper(substr(sha1(uniqid('pg_', true) . '####' . time()), 0, 15));
930
931
        if (! $topic) {
932
            $topic = $game->getTitle();
933
        }
934
935
        //
936
937
        foreach ($data['email'] as $to) {
938
            $mailSent = true;
939
            $message = $mailService->createHtmlMessage(
940
                $from,
941
                $to,
942
                $subject,
943
                'playground-game/email/' . $template,
944
                array(
945
                    'game' => $game,
946
                    'from' => $from,
947
                    'to' => $to,
948
                    'secretKey' => $secretKey,
949
                    'skinUrl' => $skinUrl,
950
                    'userTimer' => $userTimer
951
                )
952
            );
953
            try {
954
                $mailService->send($message);
955
            } catch (\Zend\Mail\Protocol\Exception\RuntimeException $e) {
956
                $mailSent = false;
957
            }
958
            
959
            if ($entry) {
960
                $shares = json_decode($entry->getSocialShares(), true);
961
                (!isset($shares['mail']))? $shares['mail'] = 1:$shares['mail'] += 1;
962
            }
963
        }
964
965
        if ($mailSent) {
966
            if ($entry) {
967
                $sharesJson = json_encode($shares);
0 ignored issues
show
Bug introduced by
The variable $shares does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
968
                $entry->setSocialShares($sharesJson);
969
                $entry = $this->getEntryMapper()->update($entry);
970
            }
971
            
972
            $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
973
                'user' => $user,
974
                'topic' => $topic,
975
                'secretKey' => $secretKey,
976
                'data' => $data,
977
                'game' => $game,
978
                'entry' => $entry
979
            ));
980
981
            return true;
982
        }
983
984
        return false;
985
    }
986
987
    /**
988
     * @param \PlaygroundGame\Entity\Game $game
989
     * @param \PlaygroundUser\Entity\User $user
990
     * @param Entry $entry
991
     * @param \PlaygroundGame\Entity\Prize $prize
992
     */
993
    public function sendResultMail($game, $user, $entry, $template = 'entry', $prize = null)
994
    {
995
        $mailService = $this->getServiceManager()->get('playgroundgame_message');
996
        $from = $this->getOptions()->getEmailFromAddress();
997
        if ($user) {
998
            $to = $user->getEmail();
999
        } elseif ($entry->getAnonymousIdentifier()) {
1000
            $to = $entry->getAnonymousIdentifier();
1001
        } else {
1002
            return false;
1003
        }
1004
        $subject = $game->getTitle();
1005
        $renderer = $this->getServiceManager()->get('Zend\View\Renderer\RendererInterface');
1006
        $skinUrl = $renderer->url(
1007
            'frontend',
1008
            array(),
1009
            array('force_canonical' => true)
1010
        );
1011
        $message = $mailService->createHtmlMessage($from, $to, $subject, 'playground-game/email/' . $template, array(
1012
            'game' => $game,
1013
            'entry' => $entry,
1014
            'skinUrl' => $skinUrl,
1015
            'prize' => $prize
1016
        ));
1017
        $mailService->send($message);
1018
    }
1019
1020
    public function sendGameMail($game, $user, $post, $template = 'postvote')
1021
    {
1022
        $mailService = $this->getServiceManager()->get('playgroundgame_message');
1023
        $from = $this->getOptions()->getEmailFromAddress();
1024
        $to = $user->getEmail();
1025
        $subject = $this->getOptions()->getParticipationSubjectLine();
1026
        $renderer = $this->getServiceManager()->get('Zend\View\Renderer\RendererInterface');
1027
        $skinUrl = $renderer->url(
1028
            'frontend',
1029
            array(),
1030
            array('force_canonical' => true)
1031
        );
1032
1033
        $message = $mailService->createHtmlMessage($from, $to, $subject, 'playground-game/email/' . $template, array(
1034
            'game' => $game,
1035
            'post' => $post,
1036
            'skinUrl' => $skinUrl
1037
        ));
1038
        $mailService->send($message);
1039
    }
1040
1041 View Code Duplication
    public function postFbWall($secretKey, $game, $user, $entry)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
1042
    {
1043
        $topic = $game->getTitle();
1044
        
1045
        $shares = json_decode($entry->getSocialShares(), true);
1046
        if (!isset($shares['fbwall'])) {
1047
            $shares['fbwall'] = 1;
1048
        } else {
1049
            $shares['fbwall'] += 1;
1050
        }
1051
        $sharesJson = json_encode($shares);
1052
        $entry->setSocialShares($sharesJson);
1053
        $entry = $this->getEntryMapper()->update($entry);
1054
        
1055
        $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
1056
            'user' => $user,
1057
            'game' => $game,
1058
            'secretKey' => $secretKey,
1059
            'topic' => $topic,
1060
            'entry' => $entry
1061
        ));
1062
1063
        return true;
1064
    }
1065
1066
    public function postFbRequest($secretKey, $game, $user, $entry, $to)
1067
    {
1068
        $shares = json_decode($entry->getSocialShares(), true);
1069
        $to = explode(',', $to);
1070
        if (!isset($shares['fbrequest'])) {
1071
            $shares['fbrequest'] = count($to);
1072
        } else {
1073
            $shares['fbrequest'] += count($to);
1074
        }
1075
        $sharesJson = json_encode($shares);
1076
        $entry->setSocialShares($sharesJson);
1077
        $entry = $this->getEntryMapper()->update($entry);
1078
        
1079
        $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
1080
            'user' => $user,
1081
            'game' => $game,
1082
            'secretKey' => $secretKey,
1083
            'entry' => $entry,
1084
            'invites' => count($to)
1085
        ));
1086
1087
        return true;
1088
    }
1089
1090 View Code Duplication
    public function postTwitter($secretKey, $game, $user, $entry)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
1091
    {
1092
        $topic = $game->getTitle();
1093
1094
        $shares = json_decode($entry->getSocialShares(), true);
1095
        if (!isset($shares['fbrequest'])) {
1096
            $shares['tweet'] = 1;
1097
        } else {
1098
            $shares['tweet'] += 1;
1099
        }
1100
        $sharesJson = json_encode($shares);
1101
        $entry->setSocialShares($sharesJson);
1102
        $entry = $this->getEntryMapper()->update($entry);
1103
        
1104
        $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
1105
            'user' => $user,
1106
            'game' => $game,
1107
            'secretKey' => $secretKey,
1108
            'topic' => $topic,
1109
            'entry' => $entry
1110
        ));
1111
1112
        return true;
1113
    }
1114
1115 View Code Duplication
    public function postGoogle($secretKey, $game, $user, $entry)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
1116
    {
1117
        $topic = $game->getTitle();
1118
        
1119
        $shares = json_decode($entry->getSocialShares(), true);
1120
        if (!isset($shares['fbrequest'])) {
1121
            $shares['google'] = 1;
1122
        } else {
1123
            $shares['google'] += 1;
1124
        }
1125
        $sharesJson = json_encode($shares);
1126
        $entry->setSocialShares($sharesJson);
1127
        $entry = $this->getEntryMapper()->update($entry);
1128
1129
        $this->getEventManager()->trigger(__FUNCTION__ . '.post', $this, array(
1130
            'user' => $user,
1131
            'game' => $game,
1132
            'secretKey' => $secretKey,
1133
            'topic' => $topic,
1134
            'entry' => $entry
1135
        ));
1136
1137
        return true;
1138
    }
1139
1140
    /**
1141
     * Is it possible to trigger a bonus entry ?
1142
     *
1143
     * @param unknown_type $game
1144
     * @param unknown_type $user
1145
     */
1146
    public function allowBonus($game, $user)
1147
    {
1148
        if (! $game->getPlayBonus() || $game->getPlayBonus() == 'none') {
1149
            return false;
1150
        } elseif ($game->getPlayBonus() == 'one') {
1151
            if ($this->getEntryMapper()->findOneBy(array(
1152
                'game' => $game,
1153
                'user' => $user,
1154
                'bonus' => 1
1155
            ))) {
1156
                return false;
1157
            } else {
1158
                return true;
1159
            }
1160
        } elseif ($game->getPlayBonus() == 'per_entry') {
1161
            return $this->getEntryMapper()->checkBonusEntry($game, $user);
1162
        }
1163
1164
        return false;
1165
    }
1166
1167
    public function addAnotherEntry($game, $user, $winner = 0)
1168
    {
1169
        $entry = new Entry();
1170
        $entry->setGame($game);
1171
        $entry->setUser($user);
1172
        $entry->setPoints(0);
1173
        $entry->setIp($this->getIp());
1174
        $entry->setActive(0);
1175
        $entry->setBonus(1);
1176
        $entry->setWinner($winner);
1177
        $entry = $this->getEntryMapper()->insert($entry);
1178
1179
        return $entry;
1180
    }
1181
1182
    /**
1183
     * This bonus entry doesn't give points nor badges
1184
     * It's just there to increase the chances during the Draw
1185
     * Old Name playBonus
1186
     *
1187
     * @param PlaygroundGame\Entity\Game $game
1188
     * @param unknown $user
1189
     * @return boolean unknown
1190
     */
1191
    public function addAnotherChance($game, $user, $winner = 0)
1192
    {
1193
        if ($this->allowBonus($game, $user)) {
1194
            $this->addAnotherEntry($game, $user, $winner);
1195
1196
            return true;
1197
        }
1198
1199
        return false;
1200
    }
1201
1202
    /**
1203
     * This bonus entry doesn't give points nor badges but can play again
1204
     *
1205
     * @param PlaygroundGame\Entity\Game $game
1206
     * @param user $user
1207
     * @return boolean unknown
1208
     */
1209
    public function playAgain($game, $user, $winner = 0)
1210
    {
1211
        if ($this->allowBonus($game, $user)) {
1212
            $entry = $this->addAnotherEntry($game, $user, $winner);
1213
            $entry->setActive(1);
1214
            $entry = $this->getEntryMapper()->update($entry);
1215
            if ($entry->getActive() == 1) {
1216
                return true;
1217
            }
1218
        }
1219
1220
        return false;
1221
    }
1222
1223
    /**
1224
     * @param string $path
1225
     */
1226
    public function uploadFile($path, $file)
1227
    {
1228
        $err = $file["error"];
1229
        $message = '';
1230
        if ($err > 0) {
1231
            switch ($err) {
1232
                case '1':
1233
                    $message .= 'Max file size exceeded. (php.ini)';
1234
                    break;
1235
                case '2':
1236
                    $message .= 'Max file size exceeded.';
1237
                    break;
1238
                case '3':
1239
                    $message .= 'File upload was only partial.';
1240
                    break;
1241
                case '4':
1242
                    $message .= 'No file was attached.';
1243
                    break;
1244
                case '7':
1245
                    $message .= 'File permission denied.';
1246
                    break;
1247
                default:
1248
                    $message .= 'Unexpected error occurs.';
1249
            }
1250
1251
            return $err;
1252
        } else {
1253
            $fileNewname = $this->fileNewname($path, $file['name'], true);
1254
1255
            if (isset($file["base64"])) {
1256
                list(, $img) = explode(',', $file["base64"]);
1257
                $img = str_replace(' ', '+', $img);
1258
                $im = base64_decode($img);
1259
                if ($im !== false) {
1260
                    // getimagesizefromstring
1261
                    file_put_contents($path . $fileNewname, $im);
1262
                } else {
1263
                    return 1;
1264
                }
1265
1266
                return $fileNewname;
1267
            } else {
1268
                $adapter = new \Zend\File\Transfer\Adapter\Http();
1269
                // 1Mo
1270
                $size = new Size(array(
1271
                    'max' => 1024000
1272
                ));
1273
                $is_image = new IsImage('jpeg,png,gif,jpg');
1274
                $adapter->setValidators(array(
1275
                    $size,
1276
                    $is_image
1277
                ), $fileNewname);
1278
1279
                if (! $adapter->isValid()) {
1280
                    return false;
1281
                }
1282
1283
                @move_uploaded_file($file["tmp_name"], $path . $fileNewname);
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
1284
            }
1285
1286
            
1287
            if (class_exists("Imagick")) {
1288
                $ext = pathinfo($fileNewname, PATHINFO_EXTENSION);
1289
                $img = new \Imagick($path . $fileNewname);
1290
                $img->cropThumbnailImage(100, 100);
1291
                $img->setImageCompression(\Imagick::COMPRESSION_JPEG);
1292
                $img->setImageCompressionQuality(75);
1293
                // Strip out unneeded meta data
1294
                $img->stripImage();
1295
                $img->writeImage($path . str_replace('.'.$ext, '-thumbnail.'.$ext, $fileNewname));
1296
                ErrorHandler::stop(true);
1297
            }
1298
        }
1299
1300
        return $fileNewname;
1301
    }
1302
1303
    /**
1304
     * @param string $path
1305
     */
1306
    public function fileNewname($path, $filename, $generate = false)
1307
    {
1308
        $sanitize = new Sanitize();
1309
        $name = $sanitize->filter($filename);
1310
        $newpath = $path . $name;
1311
1312
        if ($generate) {
1313
            if (file_exists($newpath)) {
1314
                $filename = pathinfo($name, PATHINFO_FILENAME);
1315
                $ext = pathinfo($name, PATHINFO_EXTENSION);
1316
1317
                $name = $filename . '_' . rand(0, 99) . '.' . $ext;
1318
            }
1319
        }
1320
1321
        unset($sanitize);
1322
1323
        return $name;
1324
    }
1325
1326
    /**
1327
     * This function returns the list of games, order by $type
1328
     */
1329
    public function getQueryGamesOrderBy($type = 'createdAt', $order = 'DESC')
1330
    {
1331
        $em = $this->getServiceManager()->get('doctrine.entitymanager.orm_default');
1332
        $today = new \DateTime("now");
1333
        $today = $today->format('Y-m-d') . ' 23:59:59';
1334
1335
        $onlineGames = '(
1336
            (
1337
                CASE WHEN (
1338
                    g.active = 1
1339
                    AND g.broadcastPlatform = 1
1340
                    AND (g.startDate <= :date OR g.startDate IS NULL)
1341
                    AND (g.closeDate >= :date OR g.closeDate IS NULL)
1342
                ) THEN 1 ELSE 0 END
1343
            ) +
1344
            (
1345
                CASE WHEN (
1346
                    g.active = 0
1347
                    AND (g.broadcastPlatform = 0 OR g.broadcastPlatform IS NULL)
1348
                    AND g.startDate > :date
1349
                    AND g.closeDate < :date
1350
                ) THEN 1 ELSE 0 END
1351
            )
1352
        )';
1353
1354
        $qb = $em->createQueryBuilder();
1355
        $qb->select('g')->from('PlaygroundGame\Entity\Game', 'g');
1356
        
1357
        switch ($type) {
1358
            case 'startDate':
1359
                $qb->orderBy('g.startDate', $order);
1360
                break;
1361
            case 'activeGames':
1362
                $qb->orderBy('g.active', $order);
1363
                break;
1364
            case 'onlineGames':
1365
                $qb->orderBy($onlineGames, $order);
1366
                $qb->setParameter('date', $today);
1367
                break;
1368
            case 'createdAt':
1369
                $qb->orderBy('g.createdAt', $order);
1370
                break;
1371
        }
1372
1373
        $query = $qb->getQuery();
1374
1375
        return $query;
1376
    }
1377
1378
    public function draw($game)
1379
    {
1380
        $total = $game->getWinners();
1381
1382
        // I Have to know what is the User Class used
1383
        $zfcUserOptions = $this->getServiceManager()->get('zfcuser_module_options');
1384
        $userClass = $zfcUserOptions->getUserEntityClass();
1385
1386
        $result = $this->getEntryMapper()->draw($game, $userClass, $total);
1387
1388
        foreach ($result as $e) {
1389
            $e->setWinner(1);
1390
            $e = $this->getEntryMapper()->update($e);
1391
            $this->getEventManager()->trigger('win_lottery.post', $this, array(
1392
                'user' => $e->getUser(),
1393
                'game' => $game,
1394
                'entry' => $e
1395
            ));
1396
        }
1397
1398
        return $result;
1399
    }
1400
1401
    /**
1402
     * getGameMapper
1403
     *
1404
     * @return GameMapperInterface
1405
     */
1406 View Code Duplication
    public function getGameMapper()
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
1407
    {
1408
        if (null === $this->gameMapper) {
1409
            $this->gameMapper = $this->getServiceManager()->get('playgroundgame_game_mapper');
0 ignored issues
show
Documentation Bug introduced by
It seems like $this->getServiceManager...roundgame_game_mapper') can also be of type array. However, the property $gameMapper is declared as type object<PlaygroundGame\Mapper\GameInterface>. Maybe add an additional type check?

Our type inference engine has found a suspicous assignment of a value to a property. This check raises an issue when a value that can be of a mixed type is assigned to a property that is type hinted more strictly.

For example, imagine you have a variable $accountId that can either hold an Id object or false (if there is no account id yet). Your code now assigns that value to the id property of an instance of the Account class. This class holds a proper account, so the id value must no longer be false.

Either this assignment is in error or a type check should be added for that assignment.

class Id
{
    public $id;

    public function __construct($id)
    {
        $this->id = $id;
    }

}

class Account
{
    /** @var  Id $id */
    public $id;
}

$account_id = false;

if (starsAreRight()) {
    $account_id = new Id(42);
}

$account = new Account();
if ($account instanceof Id)
{
    $account->id = $account_id;
}
Loading history...
1410
        }
1411
1412
        return $this->gameMapper;
0 ignored issues
show
Bug Compatibility introduced by
The expression $this->gameMapper; of type object|array adds the type array to the return on line 1412 which is incompatible with the return type documented by PlaygroundGame\Service\Game::getGameMapper of type PlaygroundGame\Mapper\GameInterface.
Loading history...
1413
    }
1414
1415
    /**
1416
     * setGameMapper
1417
     *
1418
     * @param GameMapperInterface $gameMapper
1419
     * @return Game
1420
     */
1421
    public function setGameMapper(GameMapperInterface $gameMapper)
1422
    {
1423
        $this->gameMapper = $gameMapper;
1424
1425
        return $this;
1426
    }
1427
1428
    /**
1429
     * getEntryMapper
1430
     *
1431
     * @return EntryMapperInterface
1432
     */
1433
    public function getEntryMapper()
1434
    {
1435
        if (null === $this->entryMapper) {
1436
            $this->entryMapper = $this->getServiceManager()->get('playgroundgame_entry_mapper');
0 ignored issues
show
Documentation Bug introduced by
It seems like $this->getServiceManager...oundgame_entry_mapper') can also be of type array. However, the property $entryMapper is declared as type object<PlaygroundGame\Se...e\EntryMapperInterface>. Maybe add an additional type check?

Our type inference engine has found a suspicous assignment of a value to a property. This check raises an issue when a value that can be of a mixed type is assigned to a property that is type hinted more strictly.

For example, imagine you have a variable $accountId that can either hold an Id object or false (if there is no account id yet). Your code now assigns that value to the id property of an instance of the Account class. This class holds a proper account, so the id value must no longer be false.

Either this assignment is in error or a type check should be added for that assignment.

class Id
{
    public $id;

    public function __construct($id)
    {
        $this->id = $id;
    }

}

class Account
{
    /** @var  Id $id */
    public $id;
}

$account_id = false;

if (starsAreRight()) {
    $account_id = new Id(42);
}

$account = new Account();
if ($account instanceof Id)
{
    $account->id = $account_id;
}
Loading history...
1437
        }
1438
1439
        return $this->entryMapper;
0 ignored issues
show
Bug Compatibility introduced by
The expression $this->entryMapper; of type object|array adds the type array to the return on line 1439 which is incompatible with the return type documented by PlaygroundGame\Service\Game::getEntryMapper of type PlaygroundGame\Service\EntryMapperInterface.
Loading history...
1440
    }
1441
1442
    /**
1443
     * setEntryMapper
1444
     *
1445
     * @param EntryMapperInterface $entryMapper
1446
     * @return Game
1447
     */
1448
    public function setEntryMapper($entryMapper)
1449
    {
1450
        $this->entryMapper = $entryMapper;
1451
1452
        return $this;
1453
    }
1454
1455
    public function setOptions(ModuleOptions $options)
1456
    {
1457
        $this->options = $options;
0 ignored issues
show
Documentation Bug introduced by
It seems like $options of type object<PlaygroundGame\Options\ModuleOptions> is incompatible with the declared type object<PlaygroundGame\Se...erviceOptionsInterface> of property $options.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
1458
1459
        return $this;
1460
    }
1461
1462
    public function getOptions()
1463
    {
1464
        if (! $this->options instanceof ModuleOptions) {
1465
            $this->setOptions($this->getServiceManager()
0 ignored issues
show
Documentation introduced by
$this->getServiceManager...ndgame_module_options') is of type object|array, but the function expects a object<PlaygroundGame\Options\ModuleOptions>.

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

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

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

function acceptsInteger($int) { }

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

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
1466
                ->get('playgroundgame_module_options'));
1467
        }
1468
1469
        return $this->options;
1470
    }
1471
1472
    /**
1473
     * Retrieve service manager instance
1474
     *
1475
     * @return ServiceManager
1476
     */
1477
    public function getServiceManager()
1478
    {
1479
        return $this->serviceManager;
1480
    }
1481
1482
    /**
1483
     * Set service manager instance
1484
     *
1485
     * @param ServiceManager $serviceManager
1486
     * @return Game
1487
     */
1488
    public function setServiceManager(ServiceManager $serviceManager)
1489
    {
1490
        $this->serviceManager = $serviceManager;
1491
1492
        return $this;
1493
    }
1494
1495
    /**
1496
     * @param string $str
1497
     */
1498
    public function getExtension($str)
1499
    {
1500
        $i = strrpos($str, '.');
1501
1502
        $l = strlen($str) - $i;
1503
        $ext = substr($str, $i + 1, $l);
1504
1505
        return $ext;
1506
    }
1507
1508
    /**
1509
     * @param string $extension
1510
     */
1511
    public function getSrc($extension, $temp_path)
1512
    {
1513
        $image_src = '';
1514
        switch ($extension) {
1515
            case 'jpg':
1516
                $image_src = imagecreatefromjpeg($temp_path);
1517
                break;
1518
            case 'jpeg':
1519
                $image_src = imagecreatefromjpeg($temp_path);
1520
                break;
1521
            case 'png':
1522
                $image_src = imagecreatefrompng($temp_path);
1523
                break;
1524
            case 'gif':
1525
                $image_src = imagecreatefromgif($temp_path);
1526
                break;
1527
        }
1528
1529
        return $image_src;
1530
    }
1531
1532
    /**
1533
     * @param string $extension
1534
     * @param string $rep
1535
     * @param integer $mini_width
1536
     * @param integer $mini_height
1537
     */
1538
    public function resize($tmp_file, $extension, $rep, $src, $mini_width, $mini_height)
0 ignored issues
show
Unused Code introduced by
The parameter $extension is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
1539
    {
1540
        list($src_width, $src_height) = getimagesize($tmp_file);
1541
1542
        $ratio_src = $src_width / $src_height;
1543
        $ratio_mini = $mini_width / $mini_height;
1544
1545
        if ($ratio_src >= $ratio_mini) {
1546
            $new_height_mini = $mini_height;
1547
            $new_width_mini = $src_width / ($src_height / $mini_height);
1548
        } else {
1549
            $new_width_mini = $mini_width;
1550
            $new_height_mini = $src_height / ($src_width / $mini_width);
1551
        }
1552
1553
        $new_image_mini = imagecreatetruecolor($mini_width, $mini_height);
1554
1555
        imagecopyresampled(
1556
            $new_image_mini,
1557
            $src,
1558
            0 - ($new_width_mini - $mini_width) / 2,
1559
            0 - ($new_height_mini - $mini_height) / 2,
1560
            0,
1561
            0,
1562
            $new_width_mini,
1563
            $new_height_mini,
1564
            $src_width,
1565
            $src_height
1566
        );
1567
        imagejpeg($new_image_mini, $rep);
1568
1569
        imagedestroy($new_image_mini);
1570
    }
1571
1572
    public function getGameEntity()
1573
    {
1574
        return new \PlaygroundGame\Entity\Game();
1575
    }
1576
1577
    /**
1578
     * @param string $resource
1579
     * @param string $privilege
1580
     */
1581
    public function isAllowed($resource, $privilege = null)
1582
    {
1583
        $auth = $this->getServiceManager()->get('BjyAuthorize\Service\Authorize');
1584
1585
        return $auth->isAllowed($resource, $privilege);
1586
    }
1587
1588
    public function getIp()
1589
    {
1590
        $ipaddress = '';
0 ignored issues
show
Unused Code introduced by
$ipaddress is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
1591
        if (isset($_SERVER['HTTP_CLIENT_IP'])) {
1592
            $ipaddress = $_SERVER['HTTP_CLIENT_IP'];
1593
        } elseif (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) {
1594
            $ipaddress = $_SERVER['HTTP_X_FORWARDED_FOR'];
1595
        } elseif (isset($_SERVER['HTTP_X_FORWARDED'])) {
1596
            $ipaddress = $_SERVER['HTTP_X_FORWARDED'];
1597
        } elseif (isset($_SERVER['HTTP_FORWARDED_FOR'])) {
1598
            $ipaddress = $_SERVER['HTTP_FORWARDED_FOR'];
1599
        } elseif (isset($_SERVER['HTTP_FORWARDED'])) {
1600
            $ipaddress = $_SERVER['HTTP_FORWARDED'];
1601
        } elseif (isset($_SERVER['REMOTE_ADDR'])) {
1602
            $ipaddress = $_SERVER['REMOTE_ADDR'];
1603
        } else {
1604
            $ipaddress = 'UNKNOWN';
1605
        }
1606
1607
        return $ipaddress;
1608
    }
1609
1610
    public function getAnonymousId()
1611
    {
1612
        $anonymousId = '';
1613
        if ($_COOKIE && array_key_exists('pg_anonymous', $_COOKIE)) {
1614
            $anonymousId = $_COOKIE['pg_anonymous'];
1615
        }
1616
1617
        return $anonymousId;
1618
    }
1619
1620
    /**
1621
     *
1622
     *
1623
     * This service is ready for all types of games
1624
     *
1625
     * @param array $data
1626
     * @return \PlaygroundGame\Entity\Game
1627
     */
1628 View Code Duplication
    public function createForm(array $data, $game, $form = null)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
1629
    {
1630
        $title = '';
1631
        $description = '';
1632
1633
        if ($data['form_jsonified']) {
1634
            $jsonPV = json_decode($data['form_jsonified']);
1635
            foreach ($jsonPV as $element) {
1636
                if ($element->form_properties) {
1637
                    $attributes = $element->form_properties[0];
1638
                    $title = $attributes->title;
1639
                    $description = $attributes->description;
1640
1641
                    break;
1642
                }
1643
            }
1644
        }
1645
        if (! $form) {
1646
            $form = new \PlaygroundGame\Entity\PlayerForm();
1647
        }
1648
        $form->setGame($game);
1649
        $form->setTitle($title);
1650
        $form->setDescription($description);
1651
        $form->setForm($data['form_jsonified']);
1652
        $form->setFormTemplate($data['form_template']);
1653
1654
        $form = $this->getPlayerFormMapper()->insert($form);
1655
1656
        return $form;
1657
    }
1658
1659
    /**
1660
     *  getCSV creates lines of CSV and returns it.
1661
     */
1662
    public function getCSV($array)
1663
    {
1664
        ob_start(); // buffer the output ...
1665
        $out = fopen('php://output', 'w');
1666
        fputcsv($out, array_keys($array[0]), ";");
1667
        foreach ($array as $line) {
1668
            fputcsv($out, $line, ";");
1669
        }
1670
        fclose($out);
1671
        return ob_get_clean(); // ... then return it as a string!
1672
    }
1673
    
1674
    public function getAttributes($attributes)
1675
    {
1676
        $a = array();
1677
1678
        $a['name']          = isset($attributes->name)? $attributes->name : '';
1679
        $a['placeholder']   = isset($attributes->data->placeholder)? $attributes->data->placeholder : '';
1680
        $a['label']         = isset($attributes->data->label)? $attributes->data->label : '';
1681
        $a['required']      = (isset($attributes->data->required) && $attributes->data->required == 'true')?
1682
            true:
1683
            false;
1684
        $a['class']         = isset($attributes->data->class)? $attributes->data->class : '';
1685
        $a['id']            = isset($attributes->data->id)? $attributes->data->id : '';
1686
        $a['lengthMin']     = isset($attributes->data->length)? $attributes->data->length->min : '';
1687
        $a['lengthMax']     = isset($attributes->data->length)? $attributes->data->length->max : '';
1688
        $a['validator']     = isset($attributes->data->validator)? $attributes->data->validator : '';
1689
        $a['innerData']     = isset($attributes->data->innerData)? $attributes->data->innerData : array();
1690
        $a['dropdownValues']= isset($attributes->data->dropdownValues)?
1691
            $attributes->data->dropdownValues :
1692
            array();
1693
        $a['filesizeMin']   = isset($attributes->data->filesize)? $attributes->data->filesize->min : 0;
1694
        $a['filesizeMax']   = isset($attributes->data->filesize)? $attributes->data->filesize->max : 10*1024*1024;
1695
1696
        return $a;
1697
    }
1698
1699
    /**
1700
     * @param \Zend\InputFilter\InputFilter $inputFilter
1701
     */
1702
    public function decorate($element, $attr, $inputFilter)
1703
    {
1704
        $factory = new InputFactory();
1705
        $element->setAttributes(
1706
            array(
1707
                'placeholder'   => $attr['placeholder'],
1708
                'required'      => $attr['required'],
1709
                'class'         => $attr['class'],
1710
                'id'            => $attr['id']
1711
            )
1712
        );
1713
1714
        $options = array();
1715
        $options['encoding'] = 'UTF-8';
1716
        if ($attr['lengthMin'] && $attr['lengthMin'] > 0) {
1717
            $options['min'] = $attr['lengthMin'];
1718
        }
1719
        if ($attr['lengthMax'] && $attr['lengthMax'] > $attr['lengthMin']) {
1720
            $options['max'] = $attr['lengthMax'];
1721
            $element->setAttribute('maxlength', $attr['lengthMax']);
1722
            $options['messages'] = array(
1723
                \Zend\Validator\StringLength::TOO_LONG => sprintf(
1724
                    $this->getServiceLocator()->get('translator')->translate(
0 ignored issues
show
Bug introduced by
The method getServiceLocator() does not seem to exist on object<PlaygroundGame\Service\Game>.

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

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

Loading history...
1725
                        'This field contains more than %s characters',
1726
                        'playgroundgame'
1727
                    ),
1728
                    $attr['lengthMax']
1729
                )
1730
            );
1731
        }
1732
1733
        $validators = array(
1734
            array(
1735
                'name'    => 'StringLength',
1736
                'options' => $options,
1737
            ),
1738
        );
1739
        if ($attr['validator']) {
1740
            $regex = "/.*\(([^)]*)\)/";
1741
            preg_match($regex, $attr['validator'], $matches);
1742
            $valArray = array(
1743
                'name' => str_replace(
1744
                    '('.$matches[1].')',
1745
                    '',
1746
                    $attr['validator']
1747
                ),
1748
                'options' => array($matches[1])
1749
            );
1750
            $validators[] = $valArray;
1751
        }
1752
1753
        $inputFilter->add($factory->createInput(array(
1754
            'name'     => $attr['name'],
1755
            'required' => $attr['required'],
1756
            'filters'  => array(
1757
                array('name' => 'StripTags'),
1758
                array('name' => 'StringTrim'),
1759
            ),
1760
            'validators' => $validators,
1761
        )));
1762
1763
        return $element;
1764
    }
1765
    /**
1766
     * Create a ZF2 Form from json data
1767
     * @return Form
1768
     */
1769
    public function createFormFromJson($jsonForm, $id = 'jsonForm')
1770
    {
1771
        $formPV = json_decode($jsonForm);
1772
        
1773
        $form = new Form();
1774
        $form->setAttribute('id', $id);
1775
        $form->setAttribute('enctype', 'multipart/form-data');
1776
        
1777
        $inputFilter = new \Zend\InputFilter\InputFilter();
1778
        $factory = new InputFactory();
1779
        
1780
        foreach ($formPV as $element) {
1781 View Code Duplication
            if (isset($element->line_text)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1782
                $attr  = $this->getAttributes($element->line_text[0]);
1783
                $element = new Element\Text($attr['name']);
1784
                $element = $this->decorate($element, $attr, $inputFilter);
1785
                $form->add($element);
1786
            }
1787 View Code Duplication
            if (isset($element->line_password)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1788
                $attr = $this->getAttributes($element->line_password[0]);
1789
                $element = new Element\Password($attr['name']);
1790
                $element = $this->decorate($element, $attr, $inputFilter);
1791
                $form->add($element);
1792
            }
1793 View Code Duplication
            if (isset($element->line_hidden)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1794
                $attr = $this->getAttributes($element->line_hidden[0]);
1795
                $element = new Element\Hidden($attr['name']);
1796
                $element = $this->decorate($element, $attr, $inputFilter);
1797
                $form->add($element);
1798
            }
1799 View Code Duplication
            if (isset($element->line_email)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1800
                $attr = $this->getAttributes($element->line_email[0]);
1801
                $element = new Element\Email($attr['name']);
1802
                $element = $this->decorate($element, $attr, $inputFilter);
1803
                $form->add($element);
1804
            }
1805 View Code Duplication
            if (isset($element->line_radio)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1806
                $attr = $this->getAttributes($element->line_radio[0]);
1807
                $element = new Element\Radio($attr['name']);
1808
1809
                $element->setLabel($attr['label']);
1810
                $element->setAttributes(
1811
                    array(
1812
                        'name'      => $attr['name'],
1813
                        'required'  => $attr['required'],
1814
                        'allowEmpty'=> !$attr['required'],
1815
                        'class'     => $attr['class'],
1816
                        'id'        => $attr['id']
1817
                    )
1818
                );
1819
                $values = array();
1820
                foreach ($attr['innerData'] as $value) {
1821
                    $values[] = $value->label;
1822
                }
1823
                $element->setValueOptions($values);
1824
        
1825
                $options = array();
1826
                $options['encoding'] = 'UTF-8';
1827
                $options['disable_inarray_validator'] = true;
1828
        
1829
                $element->setOptions($options);
1830
        
1831
                $form->add($element);
1832
        
1833
                $inputFilter->add($factory->createInput(array(
1834
                    'name'     => $attr['name'],
1835
                    'required' => $attr['required'],
1836
                    'allowEmpty' => !$attr['required'],
1837
                )));
1838
            }
1839 View Code Duplication
            if (isset($element->line_checkbox)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1840
                $attr = $this->getAttributes($element->line_checkbox[0]);
1841
                $element = new Element\MultiCheckbox($attr['name']);
1842
        
1843
                $element->setLabel($attr['label']);
1844
                $element->setAttributes(
1845
                    array(
1846
                        'name'      => $attr['name'],
1847
                        'required'  => $attr['required'],
1848
                        'allowEmpty'=> !$attr['required'],
1849
                        'class'     => $attr['class'],
1850
                        'id'        => $attr['id']
1851
                    )
1852
                );
1853
1854
                $values = array();
1855
                foreach ($attr['innerData'] as $value) {
1856
                    $values[] = $value->label;
1857
                }
1858
                $element->setValueOptions($values);
1859
                $form->add($element);
1860
        
1861
                $options = array();
1862
                $options['encoding'] = 'UTF-8';
1863
                $options['disable_inarray_validator'] = true;
1864
        
1865
                $element->setOptions($options);
1866
        
1867
                $inputFilter->add($factory->createInput(array(
1868
                    'name'      => $attr['name'],
1869
                    'required'  => $attr['required'],
1870
                    'allowEmpty'=> !$attr['required'],
1871
                )));
1872
            }
1873 View Code Duplication
            if (isset($element->line_dropdown)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1874
                $attr = $this->getAttributes($element->line_dropdown[0]);
1875
                $element = new Element\Select($attr['name']);
1876
1877
                $element->setLabel($attr['label']);
1878
                $element->setAttributes(
1879
                    array(
1880
                        'name'      => $attr['name'],
1881
                        'required'  => $attr['required'],
1882
                        'allowEmpty'=> !$attr['required'],
1883
                        'class'     => $attr['class'],
1884
                        'id'        => $attr['id']
1885
                    )
1886
                );
1887
                $values = array();
1888
                foreach ($attr['dropdownValues'] as $value) {
1889
                    $values[] = $value->dropdown_label;
1890
                }
1891
                $element->setValueOptions($values);
1892
                $form->add($element);
1893
        
1894
                $options = array();
1895
                $options['encoding'] = 'UTF-8';
1896
                $options['disable_inarray_validator'] = true;
1897
        
1898
                $element->setOptions($options);
1899
        
1900
                $inputFilter->add($factory->createInput(array(
1901
                    'name'     => $attr['name'],
1902
                    'required' => $attr['required'],
1903
                    'allowEmpty' => !$attr['required'],
1904
                )));
1905
            }
1906 View Code Duplication
            if (isset($element->line_paragraph)) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1907
                $attr = $this->getAttributes($element->line_paragraph[0]);
1908
                $element = new Element\Textarea($attr['name']);
1909
                $element = $this->decorate($element, $attr, $inputFilter);
1910
                $form->add($element);
1911
            }
1912
            if (isset($element->line_upload)) {
1913
                $attr = $this->getAttributes($element->line_upload[0]);
1914
                $element = new Element\File($attr['name']);
1915
1916
                $element->setLabel($attr['label']);
1917
                $element->setAttributes(
1918
                    array(
1919
                        'name'      => $attr['name'],
1920
                        'required'  => $attr['required'],
1921
                        'class'     => $attr['class'],
1922
                        'id'        => $attr['id']
1923
                    )
1924
                );
1925
                $form->add($element);
1926
        
1927
                $inputFilter->add($factory->createInput(array(
1928
                    'name'     => $attr['name'],
1929
                    'required' => $attr['required'],
1930
                    'validators' => array(
1931
                        array(
1932
                            'name' => '\Zend\Validator\File\Size',
1933
                            'options' => array('min' => $attr['filesizeMin'], 'max' => $attr['filesizeMax'])
1934
                        ),
1935
                        array(
1936
                            'name' => '\Zend\Validator\File\Extension',
1937
                            'options'  => array(
1938
                                'png,PNG,jpg,JPG,jpeg,JPEG,gif,GIF',
1939
                                'messages' => array(
1940
                                    \Zend\Validator\File\Extension::FALSE_EXTENSION =>'Veuillez télécharger une image'
1941
                                )
1942
                            )
1943
                        ),
1944
                    ),
1945
                )));
1946
            }
1947
        }
1948
        
1949
        $form->setInputFilter($inputFilter);
1950
        
1951
        return $form;
1952
    }
1953
1954
    /**
1955
     * Send mail for winner and/or loser
1956
     * @param \PlaygroundGame\Entity\Game $game
1957
     * @param \PlaygroundUser\Entity\User $user
1958
     * @param \PlaygroundGame\Entity\Entry $lastEntry
1959
     * @param \PlaygroundGame\Entity\Prize $prize
1960
     */
1961
    public function sendMail($game, $user, $lastEntry, $prize = null)
1962
    {
1963 View Code Duplication
        if (($user || ($game->getAnonymousAllowed() && $game->getAnonymousIdentifier())) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1964
            $game->getMailWinner() &&
1965
            $lastEntry->getWinner()
1966
        ) {
1967
            $this->sendResultMail($game, $user, $lastEntry, 'winner', $prize);
1968
        }
1969
1970 View Code Duplication
        if (($user || ($game->getAnonymousAllowed() && $game->getAnonymousIdentifier())) &&
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

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

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

Loading history...
1971
            $game->getMailLooser() &&
1972
            !$lastEntry->getWinner()
1973
        ) {
1974
            $this->sendResultMail($game, $user, $lastEntry, 'looser');
1975
        }
1976
    }
1977
1978
    public function getPlayerFormMapper()
1979
    {
1980
        if (null === $this->playerformMapper) {
1981
            $this->playerformMapper = $this->getServiceManager()->get('playgroundgame_playerform_mapper');
1982
        }
1983
1984
        return $this->playerformMapper;
1985
    }
1986
1987
    public function setPlayerFormMapper($playerformMapper)
1988
    {
1989
        $this->playerformMapper = $playerformMapper;
1990
1991
        return $this;
1992
    }
1993
1994
    public function getInvitationMapper()
1995
    {
1996
        if (null === $this->invitationMapper) {
1997
            $this->invitationMapper = $this->getServiceManager()->get('playgroundgame_invitation_mapper');
1998
        }
1999
2000
        return $this->invitationMapper;
2001
    }
2002
2003
    public function setInvitationMapper($invitationMapper)
2004
    {
2005
        $this->invitationMapper = $invitationMapper;
2006
2007
        return $this;
2008
    }
2009
}
2010