Completed
Branch master (ae19d9)
by Pierre-Henry
36:56
created

MailModel::search()   D

Complexity

Conditions 11
Paths 512

Size

Total Lines 62
Code Lines 38

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 11
eloc 38
nc 512
nop 8
dl 0
loc 62
rs 4.0298
c 0
b 0
f 0

How to fix   Long Method    Complexity    Many Parameters   

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:

Many Parameters

Methods with many parameters are not only hard to understand, but their parameters also often become inconsistent when you need more, or different data.

There are several approaches to avoid long parameter lists:

1
<?php
2
/**
3
 * @author         Pierre-Henry Soria <[email protected]>
4
 * @copyright      (c) 2012-2017, Pierre-Henry Soria. All Rights Reserved.
5
 * @license        GNU General Public License; See PH7.LICENSE.txt and PH7.COPYRIGHT.txt in the root directory.
6
 * @package        PH7 / App / System / Module / Mail / Model
7
 */
8
9
namespace PH7;
10
11
use PH7\Framework\Mvc\Model\Spam as SpamModel;
12
use PH7\Framework\Mvc\Model\Engine\Db;
0 ignored issues
show
Bug introduced by
This use statement conflicts with another class in this namespace, PH7\Db.

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

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

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

// Bar.php
namespace OtherDir;

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

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

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

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

// Bar.php
namespace OtherDir;

use SomeDir\Foo as SomeDirFoo; // There is no conflict anymore.
Loading history...
13
use PH7\Framework\Error\CException\PH7InvalidArgumentException;
14
15
class MailModel extends MailCoreModel
16
{
17
    const INBOX = 1, OUTBOX = 2, TRASH = 3;
18
19
    const TRASH_MODE = 'trash';
20
    const RESTOR_MODE = 'restor';
21
    const DELETE_MODE = 'delete';
22
23
    const MODES = [
24
        self::TRASH_MODE,
25
        self::RESTOR_MODE,
26
        self::DELETE_MODE
27
    ];
28
29
    public function readMsg($iRecipient, $iMessageId)
30
    {
31
        $rStmt = Db::getInstance()->prepare(
32
            'SELECT msg.*, m.profileId, m.username, m.firstName FROM' . Db::prefix('Messages') .
33
            'AS msg LEFT JOIN ' . Db::prefix('Members') . 'AS m ON msg.sender = m.profileId
34
            WHERE msg.recipient = :recipient AND msg.messageId = :messageId AND NOT FIND_IN_SET(\'recipient\', msg.trash) LIMIT 1'
35
        );
36
37
        $rStmt->bindValue(':recipient', $iRecipient, \PDO::PARAM_INT);
38
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
39
        $rStmt->execute();
40
        return $rStmt->fetch(\PDO::FETCH_OBJ);
41
    }
42
43
    public function readSentMsg($iSender, $iMessageId)
44
    {
45
        $rStmt = Db::getInstance()->prepare(
46
            'SELECT msg.*, m.profileId, m.username, m.firstName FROM' . Db::prefix('Messages') .
47
            'AS msg LEFT JOIN ' . Db::prefix('Members') . 'AS m ON msg.recipient = m.profileId
48
            WHERE msg.sender = :sender AND msg.messageId = :messageId AND NOT FIND_IN_SET(\'sender\', msg.toDelete) LIMIT 1'
49
        );
50
51
        $rStmt->bindValue(':sender', $iSender, \PDO::PARAM_INT);
52
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
53
        $rStmt->execute();
54
        return $rStmt->fetch(\PDO::FETCH_OBJ);
55
    }
56
57
    public function readTrashMsg($iProfileId, $iMessageId)
58
    {
59
        $rStmt = Db::getInstance()->prepare(
60
            'SELECT msg.*, m.profileId, m.username, m.firstName FROM' . Db::prefix('Messages') .
61
            'AS msg LEFT JOIN ' . Db::prefix('Members') . 'AS m ON msg.sender = m.profileId
62
            WHERE msg.recipient = :profileId AND msg.messageId = :messageId AND FIND_IN_SET(\'recipient\', msg.trash)
63
            AND NOT FIND_IN_SET(\'recipient\', msg.toDelete) LIMIT 1'
64
        );
65
66
        $rStmt->bindValue(':profileId', $iProfileId, \PDO::PARAM_INT);
67
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
68
        $rStmt->execute();
69
        return $rStmt->fetch(\PDO::FETCH_OBJ);
70
    }
71
72
    /**
73
     * Send a message.
74
     *
75
     * @param integer $iSender
76
     * @param integer $iRecipient
77
     * @param string $sTitle
78
     * @param string $sMessage
79
     * @param string $sCreatedDate
80
     *
81
     * @return boolean|integer Returns the ID of the message on success or FALSE on failure.
82
     */
83
    public function sendMsg($iSender, $iRecipient, $sTitle, $sMessage, $sCreatedDate)
84
    {
85
        $rStmt = Db::getInstance()->prepare(
86
            'INSERT INTO' . Db::prefix('Messages') . '(sender, recipient, title, message, sendDate, status)
87
            VALUES (:sender, :recipient, :title, :message, :sendDate, \'1\')'
88
        );
89
        $rStmt->bindValue(':sender', $iSender, \PDO::PARAM_INT);
90
        $rStmt->bindValue(':recipient', $iRecipient, \PDO::PARAM_INT);
91
        $rStmt->bindValue(':title', $sTitle, \PDO::PARAM_STR);
92
        $rStmt->bindValue(':message', $sMessage, \PDO::PARAM_STR);
93
        $rStmt->bindValue(':sendDate', $sCreatedDate, \PDO::PARAM_STR);
94
        return (!$rStmt->execute()) ? false : Db::getInstance()->lastInsertId();
95
    }
96
97
    public function deleteMsg($iRecipient, $iMessageId)
98
    {
99
        $rStmt = Db::getInstance()->prepare('DELETE FROM' . Db::prefix('Messages') . 'WHERE recipient = :recipient AND messageId = :messageId LIMIT 1');
100
        $rStmt->bindValue(':recipient', $iRecipient, \PDO::PARAM_INT);
101
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
102
        return $rStmt->execute();
103
    }
104
105
    public function adminDeleteMsg($iMessageId)
106
    {
107
        $rStmt = Db::getInstance()->prepare('DELETE FROM' . Db::prefix('Messages') . 'WHERE messageId = :messageId LIMIT 1');
108
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
109
        return $rStmt->execute();
110
    }
111
112
    public function setReadMsg($iMessageId)
113
    {
114
        $rStmt = Db::getInstance()->prepare('UPDATE' . Db::prefix('Messages') . 'SET status = 0 WHERE messageId = :messageId LIMIT 1');
115
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
116
        $rStmt->execute();
117
        Db::free($rStmt);
118
    }
119
120
    public function getMsg($iMessageId)
121
    {
122
        $rStmt = Db::getInstance()->prepare('SELECT * FROM' . Db::prefix('Messages') . 'WHERE messageId = :messageId LIMIT 1');
123
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
124
        $rStmt->execute();
125
        return $rStmt->fetch(\PDO::FETCH_OBJ);
126
    }
127
128
    /**
129
     * Set message to 'trash' or 'toDelete'.
130
     *
131
     * @param integer $iProfileId User ID
132
     * @param integer $iMessageId Message ID
133
     * @param string $sMode Set to this category. Choose between 'trash', 'restor' and 'delete'
134
     *
135
     * @throws PH7InvalidArgumentException
136
     *
137
     * @return void
138
     */
139
    public function setTo($iProfileId, $iMessageId, $sMode)
140
    {
141
        if (!in_array($sMode, self::MODES)) {
142
            throw new PH7InvalidArgumentException('Bad set mode: "' . $sMode . '"!');
143
        }
144
145
        $oData = $this->getMsg($iMessageId);
146
        $sFieldId = ($oData->sender == $iProfileId) ? 'sender' : 'recipient';
147
        if ($sMode == self::RESTOR_MODE) {
148
            $sTrashVal = str_replace(array($sFieldId, ','), '', $oData->trash);
149
        } else {
150
            $sTrashVal = ($oData->sender == $oData->recipient) ? 'sender,recipient' : $sFieldId . (!empty($oData->trash) ? ',' . $oData->trash : '');
151
        }
152
        unset($oData);
153
154
        $sField = ($sMode == self::DELETE_MODE) ? 'toDelete' : 'trash';
155
        $rStmt = Db::getInstance()->prepare('UPDATE' . Db::prefix('Messages') . 'SET ' . $sField . ' = :val WHERE ' . $sFieldId . ' = :profileId AND messageId = :messageId LIMIT 1');
156
        $rStmt->bindValue(':profileId', $iProfileId, \PDO::PARAM_INT);
157
        $rStmt->bindValue(':messageId', $iMessageId, \PDO::PARAM_INT);
158
        $rStmt->bindValue(':val', $sTrashVal, \PDO::PARAM_STR);
159
160
        return $rStmt->execute();
161
    }
162
163
    /**
164
     * @param integer|string $mLooking
165
     * @param boolean $bCount
166
     * @param string $sOrderBy
167
     * @param string $sSort
168
     * @param integer $iOffset
169
     * @param integer $iLimit
170
     * @param integer|null $iProfileId
171
     * @param string $sType
172
     *
173
     * @return integer|object
174
     */
175
    public function search($mLooking, $bCount, $sOrderBy, $sSort, $iOffset, $iLimit, $iProfileId = null, $sType = 'all')
176
    {
177
        $bCount = (bool) $bCount;
178
        $iOffset = (int) $iOffset;
179
        $iLimit = (int) $iLimit;
180
        $mLooking = trim($mLooking);
181
182
        $sSqlLimit = (!$bCount) ? ' LIMIT :offset, :limit' : '';
183
        $sSqlSelect = (!$bCount) ? '*' : 'COUNT(messageId) AS totalMails';
184
        $sSqlFind = ' ' . (ctype_digit($mLooking) ? '(messageId = :looking)' : '(title LIKE :looking OR message LIKE :looking OR username LIKE :looking OR firstName LIKE :looking OR lastName LIKE :looking)');
185
        $sSqlOrder = SearchCoreModel::order($sOrderBy, $sSort);
186
187
        switch ($sType)
188
        {
189
            case self::INBOX:
190
                $sSql = 'msg.sender = m.profileId WHERE (msg.recipient = :profileId) AND (NOT FIND_IN_SET(\'recipient\', msg.trash)) AND';
191
            break;
192
193
            case self::OUTBOX:
194
                $sSql = 'msg.recipient = m.profileId WHERE (msg.sender = :profileId) AND (NOT FIND_IN_SET(\'sender\', msg.toDelete)) AND';
195
            break;
196
197
            case self::TRASH:
198
                $sSql = 'msg.sender = m.profileId WHERE (msg.recipient = :profileId) AND (FIND_IN_SET(\'recipient\', msg.trash)) AND
199
                (NOT FIND_IN_SET(\'recipient\', msg.toDelete)) AND';
200
            break;
201
202
            default:
203
                // All messages
204
                $sSql = 'msg.sender = m.profileId WHERE ';
205
        }
206
207
        $rStmt = Db::getInstance()->prepare('SELECT ' . $sSqlSelect . ' FROM' . Db::prefix('Messages') . 'AS msg LEFT JOIN ' . Db::prefix('Members') . 'AS m ON ' .
208
        $sSql . $sSqlFind . $sSqlOrder . $sSqlLimit);
209
210
        (ctype_digit($mLooking)) ? $rStmt->bindValue(':looking', $mLooking, \PDO::PARAM_INT) : $rStmt->bindValue(':looking', '%' . $mLooking . '%', \PDO::PARAM_STR);
211
212
        if (!empty($iProfileId))
213
            $rStmt->bindParam(':profileId', $iProfileId, \PDO::PARAM_INT);
214
215
        if (!$bCount)
216
        {
217
            $rStmt->bindParam(':offset', $iOffset, \PDO::PARAM_INT);
218
            $rStmt->bindParam(':limit', $iLimit, \PDO::PARAM_INT);
219
        }
220
221
        $rStmt->execute();
222
223
        if (!$bCount)
224
        {
225
            $mData = $rStmt->fetchAll(\PDO::FETCH_OBJ);
226
        }
227
        else
228
        {
229
            $oRow = $rStmt->fetch(\PDO::FETCH_OBJ);
230
            $mData = (int) $oRow->totalMails;
231
            unset($oRow);
232
        }
233
234
        Db::free($rStmt);
235
        return $mData;
236
    }
237
238
    /**
239
     * Check Duplicate Contents.
240
     *
241
     * @param integer $iSenderId Sender's ID
242
     * @param string $sMsg Message content
243
     *
244
     * @return boolean Returns TRUE if similar content was found in the table, FALSE otherwise.
245
     */
246
    public function isDuplicateContent($iSenderId, $sMsg)
247
    {
248
        return SpamModel::detectDuplicate(
249
            $sMsg,
250
            'message',
251
            'sender',
252
            $iSenderId,
253
            'Messages',
254
            'AND NOT FIND_IN_SET(\'recipient\', toDelete)'
255
        );
256
    }
257
258
    /**
259
     * To prevent spam!
260
     *
261
     * @param integer $iSenderId
262
     * @param integer $iWaitTime In minutes!
263
     * @param string $sCurrentTime In date format: 0000-00-00 00:00:00
264
     *
265
     * @return boolean Return TRUE if the weather was fine, otherwise FALSE
266
     */
267
    public function checkWaitSend($iSenderId, $iWaitTime, $sCurrentTime)
268
    {
269
        $rStmt = Db::getInstance()->prepare('SELECT messageId FROM' . Db::prefix('Messages') . 'WHERE sender = :sender AND DATE_ADD(sendDate, INTERVAL :waitTime MINUTE) > :currentTime LIMIT 1');
270
        $rStmt->bindValue(':sender', $iSenderId, \PDO::PARAM_INT);
271
        $rStmt->bindValue(':waitTime', $iWaitTime, \PDO::PARAM_INT);
272
        $rStmt->bindValue(':currentTime', $sCurrentTime, \PDO::PARAM_STR);
273
        $rStmt->execute();
274
        return ($rStmt->rowCount() === 0);
275
    }
276
}
277