Browse Source

fix merge with master

Bastien Sevajol 6 years ago
parent
commit
32b896ebfb
1 changed files with 58 additions and 11 deletions
  1. 58 11
      tracim/tracim/lib/email_fetcher.py

+ 58 - 11
tracim/tracim/lib/email_fetcher.py View File

@@ -1,10 +1,12 @@
1 1
 # -*- coding: utf-8 -*-
2 2
 
3
-import imaplib
4 3
 import time
4
+import imaplib
5
+import json
5 6
 import typing
6 7
 from email import message_from_bytes
7
-from email.header import decode_header, make_header
8
+from email.header import decode_header
9
+from email.header import make_header
8 10
 from email.message import Message
9 11
 from email.utils import parseaddr
10 12
 
@@ -177,7 +179,9 @@ class MailFetcher(object):
177 179
         self._is_active = True
178 180
 
179 181
     def run(self) -> None:
182
+        logger.info(self, 'Starting MailFetcher')
180 183
         while self._is_active:
184
+            logger.debug(self, 'sleep for {}'.format(self.delay))
181 185
             time.sleep(self.delay)
182 186
             try:
183 187
                 self._connect()
@@ -200,20 +204,32 @@ class MailFetcher(object):
200 204
         # TODO - G.M - 2017-11-15 Verify connection/disconnection
201 205
         # Are old connexion properly close this way ?
202 206
         if self._connection:
207
+            logger.debug(self, 'Disconnect from IMAP')
203 208
             self._disconnect()
204 209
         # TODO - G.M - 2017-11-23 Support for predefined SSLContext ?
205 210
         # without ssl_context param, tracim use default security configuration
206 211
         # which is great in most case.
207 212
         if self.use_ssl:
213
+            logger.debug(self, 'Connect IMAP {}:{} using SSL'.format(
214
+                self.host,
215
+                self.port,
216
+            ))
208 217
             self._connection = imaplib.IMAP4_SSL(self.host, self.port)
209 218
         else:
219
+            logger.debug(self, 'Connect IMAP {}:{}'.format(
220
+                self.host,
221
+                self.port,
222
+            ))
210 223
             self._connection = imaplib.IMAP4(self.host, self.port)
211 224
 
212 225
         try:
226
+            logger.debug(self, 'Login IMAP with login {}'.format(
227
+                self.user,
228
+            ))
213 229
             self._connection.login(self.user, self.password)
214 230
         except Exception as e:
215 231
             log = 'IMAP login error: {}'
216
-            logger.warning(self, log.format(e.__str__()))
232
+            logger.error(self, log.format(e.__str__()))
217 233
 
218 234
     def _disconnect(self) -> None:
219 235
         if self._connection:
@@ -228,33 +244,52 @@ class MailFetcher(object):
228 244
         """
229 245
         messages = []
230 246
         # select mailbox
247
+        logger.debug(self, 'Fetch messages from folder {}'.format(
248
+            self.folder,
249
+        ))
231 250
         rv, data = self._connection.select(self.folder)
251
+        logger.debug(self, 'Response status {}'.format(
252
+            rv,
253
+        ))
232 254
         if rv == 'OK':
233 255
             # get mails
234 256
             # TODO - G.M -  2017-11-15 Which files to select as new file ?
235 257
             # Unseen file or All file from a directory (old one should be
236 258
             #  moved/ deleted from mailbox during this process) ?
259
+            logger.debug(self, 'Fetch unseen messages')
237 260
             rv, data = self._connection.search(None, "(UNSEEN)")
261
+            logger.debug(self, 'Response status {}'.format(
262
+                rv,
263
+            ))
238 264
             if rv == 'OK':
239 265
                 # get mail content
266
+                logger.debug(self, 'Found {} unseen mails'.format(
267
+                    len(data[0].split()),
268
+                ))
240 269
                 for num in data[0].split():
241 270
                     # INFO - G.M - 2017-11-23 - Fetch (RFC288) to retrieve all
242 271
                     # complete mails see example : https://docs.python.org/fr/3.5/library/imaplib.html#imap4-example .  # nopep8
243 272
                     # Be careful, This method remove also mails from Unseen
244 273
                     # mails
274
+                    logger.debug(self, 'Fetch mail "{}"'.format(
275
+                        num,
276
+                    ))
245 277
                     rv, data = self._connection.fetch(num, '(RFC822)')
278
+                    logger.debug(self, 'Response status {}'.format(
279
+                        rv,
280
+                    ))
246 281
                     if rv == 'OK':
247 282
                         msg = message_from_bytes(data[0][1])
248 283
                         messages.append(msg)
249 284
                     else:
250 285
                         log = 'IMAP : Unable to get mail : {}'
251
-                        logger.debug(self, log.format(str(rv)))
286
+                        logger.error(self, log.format(str(rv)))
252 287
             else:
253
-                # FIXME : Distinct error from empty mailbox ?
254
-                pass
288
+                log = 'IMAP : Unable to get unseen mail : {}'
289
+                logger.error(self, log.format(str(rv)))
255 290
         else:
256 291
             log = 'IMAP : Unable to open mailbox : {}'
257
-            logger.debug(self, log.format(str(rv)))
292
+            logger.error(self, log.format(str(rv)))
258 293
         return messages
259 294
 
260 295
     def _notify_tracim(
@@ -266,6 +301,9 @@ class MailFetcher(object):
266 301
         :param mails: list of mails to send
267 302
         :return: unsended mails
268 303
         """
304
+        logger.debug(self, 'Notify tracim about {} new responses'.format(
305
+            len(mails),
306
+        ))
269 307
         unsended_mails = []
270 308
         # TODO BS 20171124: Look around mail.get_from_address(), mail.get_key()
271 309
         # , mail.get_body() etc ... for raise InvalidEmailError if missing
@@ -282,19 +320,28 @@ class MailFetcher(object):
282 320
                            use_txt_parsing=self.use_txt_parsing),
283 321
                    }}
284 322
             try:
323
+                logger.debug(
324
+                    self,
325
+                    'Contact API on {} with body {}'.format(
326
+                        self.endpoint,
327
+                        json.dumps(msg),
328
+                    ),
329
+                )
285 330
                 r = requests.post(self.endpoint, json=msg)
286 331
                 if r.status_code not in [200, 204]:
287
-                    log = 'bad status code response when sending mail to tracim: {}'  # nopep8
288
-                    logger.error(self, log.format(str(r.status_code)))
332
+                    details = r.json().get('msg')
333
+                    log = 'bad status code {} response when sending mail to tracim: {}'  # nopep8
334
+                    logger.error(self, log.format(
335
+                        str(r.status_code),
336
+                        details,
337
+                    ))
289 338
             # TODO - G.M - Verify exception correctly works
290 339
             except requests.exceptions.Timeout as e:
291 340
                 log = 'Timeout error to transmit fetched mail to tracim : {}'
292 341
                 logger.error(self, log.format(str(e)))
293 342
                 unsended_mails.append(mail)
294
-                break
295 343
             except requests.exceptions.RequestException as e:
296 344
                 log = 'Fail to transmit fetched mail to tracim : {}'
297 345
                 logger.error(self, log.format(str(e)))
298
-                break
299 346
 
300 347
         return unsended_mails