Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
93.75% covered (success)
93.75%
90 / 96
83.33% covered (success)
83.33%
5 / 6
CRAP
0.00% covered (danger)
0.00%
0 / 1
Office365
93.75% covered (success)
93.75%
90 / 96
83.33% covered (success)
83.33%
5 / 6
29.21
0.00% covered (danger)
0.00%
0 / 1
 getMessages
88.89% covered (success)
88.89%
48 / 54
0.00% covered (danger)
0.00%
0 / 1
19.50
 getMessage
100.00% covered (success)
100.00%
11 / 11
100.00% covered (success)
100.00%
1 / 1
3
 getAttachments
100.00% covered (success)
100.00%
10 / 10
100.00% covered (success)
100.00%
1 / 1
2
 getAttachment
100.00% covered (success)
100.00%
10 / 10
100.00% covered (success)
100.00%
1 / 1
2
 markAsRead
100.00% covered (success)
100.00%
10 / 10
100.00% covered (success)
100.00%
1 / 1
2
 markAsUnread
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2declare(strict_types=1);
3/**
4 * Pop PHP Framework (https://www.popphp.org/)
5 *
6 * @link       https://github.com/popphp/popphp-framework
7 * @author     Nick Sagona, III <dev@noladev.com>
8 * @copyright  Copyright (c) 2009-2027 NOLA Interactive, LLC.
9 * @license    https://www.popphp.org/license     New BSD License
10 */
11
12/**
13 * @namespace
14 */
15namespace Pop\Mail\Client;
16
17use Pop\Http;
18use Pop\Mail\Api\AbstractOffice365;
19
20/**
21 * Office 365 mail client class
22 *
23 * @category   Pop
24 * @package    Pop\Mail
25 * @author     Nick Sagona, III <dev@noladev.com>
26 * @copyright  Copyright (c) 2009-2027 NOLA Interactive, LLC.
27 * @license    https://www.popphp.org/license     New BSD License
28 * @version    5.0.0
29 */
30class Office365 extends AbstractOffice365 implements HttpClientInterface
31{
32
33    /**
34     * Get messages
35     *
36     * @param  string $folder
37     * @param  array  $search
38     * @param  int    $limit
39     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
40     * @return mixed
41     */
42    public function getMessages(string $folder = 'Inbox', array $search = [], int $limit = 10): mixed
43    {
44        if ($this->client === null) {
45            throw new Exception('Error: The client object has not been instantiated yet.');
46        }
47
48        $this->verifyToken();
49
50        $data = [];
51
52        if (!empty($limit)) {
53            $data['$top'] = $limit;
54        }
55
56        if (!empty($search)) {
57            $filterStrings = [];
58            foreach ($search as $key => $value) {
59                $op         = 'eq';
60                $startsWith = false;
61                $endsWith   = false;
62                if (str_ends_with($key, '%')) {
63                    $startsWith = true;
64                    $key        = substr($key, 0, -1);
65                } else if (str_starts_with($key, '%')) {
66                    $endsWith = true;
67                    $key      = substr($key, 1);
68                } else {
69                    if (str_ends_with($key, '!=')) {
70                        $op  = 'ne';
71                        $key = substr($key, 0, -2);
72                    } else if (str_ends_with($key, '>')) {
73                        $op  = 'gt';
74                        $key = substr($key, 0, -1);
75                    } else if (str_ends_with($key, '>=')) {
76                        $op  = 'ge';
77                        $key = substr($key, 0, -2);
78                    } else if (str_ends_with($key, '<')) {
79                        $op  = 'lt';
80                        $key = substr($key, 0, -1);
81                    } else if (str_ends_with($key, '<=')) {
82                        $op  = 'le';
83                        $key = substr($key, 0, -2);
84                    }
85                }
86
87                switch (strtolower($key)) {
88                    case 'unread':
89                        $filterStrings[] = "isRead " . $op . " " . ($value ? "false" : "true");
90                        break;
91                    case 'sent':
92                        $filterStrings[] = "sentDateTime " . $op . " " . date('c', strtotime($value));
93                        break;
94                    default:
95                        if ($startsWith) {
96                            $filterStrings[] = "startsWith(" . $key . ", '" . $value . "')";
97                        } else if ($endsWith) {
98                            $filterStrings[] = "endsWith(" . $key . ", '" . $value . "')";
99                        } else {
100                            $filterStrings[] = $key . " " . $op . " '" . $value . "'";
101                        }
102                }
103            }
104
105            $data['filter'] = implode(' and ', $filterStrings);
106        }
107
108        $this->client->setAuth(Http\Auth::createBearer($this->token));
109        $this->client->addOption('method', 'GET');
110        $this->client->addOption('type', Http\Client\Request::URLENCODED);
111        $this->client->addOption('auto', true);
112
113        $uri = "/" . $this->accountId . "/mailfolders('" . $folder . "')/messages";
114        if (!empty($data)){
115            $uri .= '?' . rawurldecode(http_build_query($data, "\n"));
116        }
117
118        return $this->client->send($uri);
119    }
120
121    /**
122     * Get messages
123     *
124     * @param  string $messageId
125     * @param  bool   $raw
126     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
127     * @return mixed
128     */
129    public function getMessage(string $messageId, bool $raw = false): mixed
130    {
131        if ($this->client === null) {
132            throw new Exception('Error: The client object has not been instantiated yet.');
133        }
134
135        $this->verifyToken();
136
137        $this->client->setAuth(Http\Auth::createBearer($this->token));
138        $this->client->addOption('method', 'GET');
139        $this->client->addOption('type', Http\Client\Request::URLENCODED);
140        $this->client->addOption('auto', true);
141
142        $uri = "/" . $this->accountId . "/messages/" . $messageId;
143        if ($raw) {
144            $uri .= '/$value';
145        }
146
147        return $this->client->send($uri);
148    }
149
150    /**
151     * Get message attachments
152     *
153     * @param  string $messageId
154     * @param  string $folder
155     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
156     * @return mixed
157     */
158    public function getAttachments(string $messageId, string $folder = 'Inbox'): mixed
159    {
160        if ($this->client === null) {
161            throw new Exception('Error: The client object has not been instantiated yet.');
162        }
163
164        $this->verifyToken();
165
166        $this->client->setAuth(Http\Auth::createBearer($this->token));
167        $this->client->addOption('method', 'GET');
168        $this->client->addOption('type', Http\Client\Request::URLENCODED);
169        $this->client->addOption('auto', true);
170
171        return $this->client->send(
172            "/" . $this->accountId . "/mailfolders('" . $folder . "')/messages/" . $messageId . "/attachments"
173        );
174    }
175
176    /**
177     * Get message attachment
178     *
179     * @param  string $messageId
180     * @param  string $attachmentId
181     * @param  string $folder
182     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
183     * @return mixed
184     */
185    public function getAttachment(string $messageId, string $attachmentId, string $folder = 'Inbox'): mixed
186    {
187        if ($this->client === null) {
188            throw new Exception('Error: The client object has not been instantiated yet.');
189        }
190
191        $this->verifyToken();
192
193        $this->client->setAuth(Http\Auth::createBearer($this->token));
194        $this->client->addOption('method', 'GET');
195        $this->client->addOption('type', Http\Client\Request::URLENCODED);
196        $this->client->addOption('auto', true);
197
198        return $this->client->send(
199            "/" . $this->accountId . "/mailfolders('" . $folder . "')/messages/" . $messageId . "/attachments/" . $attachmentId
200        );
201    }
202
203    /**
204     * Mark message as read
205     *
206     * @param  string $messageId
207     * @param  bool   $isRead
208     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
209     * @return Office365
210     */
211    public function markAsRead(string $messageId, bool $isRead = true): Office365
212    {
213        if ($this->client === null) {
214            throw new Exception('Error: The client object has not been instantiated yet.');
215        }
216
217        $this->verifyToken();
218
219        $this->client->setAuth(Http\Auth::createBearer($this->token));
220        $this->client->addOption('type', Http\Client\Request::JSON);
221        $this->client->addOption('auto', true);
222        $this->client->addOption('method', 'PATCH');
223        $this->client->setData(['isRead' => $isRead]);
224
225        $this->client->send("/" . $this->accountId . "/messages/" . $messageId);
226
227        return $this;
228    }
229
230    /**
231     * Mark message as unread
232     *
233     * @param  string $messageId
234     * @throws Exception|Http\Exception|Http\Client\Exception|Http\Client\Handler\Exception
235     * @return Office365
236     */
237    public function markAsUnread(string $messageId): Office365
238    {
239        return $this->markAsRead($messageId, false);
240    }
241
242}