Beispiel #1
0
 def _export_folder_subset(self, folder, start_dt=None, end_dt=None):
     """ Export a time-subset of an exchange folder
     :param folder: The exchange folder to export
     :start_dt: The start date to export from, default 1900-01-01
     :end_dt: The end date to export to, default 2100-01-01
     :return: Number of attachments in folder
     """
     try:
         logger.info('Export subset: {} to {}'.format(start_dt, end_dt))
         attachments = 0
         if start_dt is None:
             start_dt = EWSDate(1900, 1, 1)
         if end_dt is None:
             end_dt = EWSDate(2100, 1, 1)
         items = folder.all()
         start_dt = UTC.localize(
             EWSDateTime(start_dt.year, start_dt.month, start_dt.day, 0, 0))
         end_dt = UTC.localize(
             EWSDateTime(end_dt.year, end_dt.month, end_dt.day, 0, 0))
         items = items.filter(datetime_received__range=(start_dt, end_dt))
         for chunk in chunkify(items, 10):
             for item in chunk:
                 self.actual_exported_mails += 1
                 logger.error(
                     str(item.datetime_created) + ':' + str(item.subject))
                 skip_list = self.export_item_body(item)
                 attachments += self.export_attachments(item, skip_list)
         self.update_amqp(only_mails=True)
     except ErrorMimeContentConversionFailed:
         msg = '{}: ErrorMimeContentConversionFailed, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))
     except ErrorInternalServerError:
         # Possibly happens on p7m files?
         msg = '{}: ErrorInternalServerError, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))
     except ErrorInvalidOperation:
         msg = '{}: ErrorInvalidOperation, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))
     except ErrorTimeoutExpired:
         attachments = -1
         time.sleep(30)
         logger.warning('{}: ErrorTimeoutExpired'.format(self.export_path))
     except ErrorInternalServerTransientError:
         attachments = -1
         time.sleep(30)
         warning = '{}, {}: ErrorInternalServerTransientError'
         logger.warning(warning.format(self.export_path, folder))
     return attachments
 def _export_folder_subset(self, folder, start_dt=None, end_dt=None):
     """ Export a time-subset of an exchange folder
     :param folder: The exchange folder to export
     :start_dt: The start date to export from, default 1900-01-01
     :end_dt: The end date to export to, default 2100-01-01
     :return: Number of attachments in folder
     """
     try:
         logger.info('Export subset: {} to {}'.format(start_dt, end_dt))
         attachments = 0
         if start_dt is None:
             start_dt = EWSDate(1900, 1, 1)
         if end_dt is None:
             end_dt = EWSDate(2100, 1, 1)
         items = folder.all()
         start_dt = UTC.localize(EWSDateTime(start_dt.year, start_dt.month,
                                             start_dt.day, 0, 0))
         end_dt = UTC.localize(EWSDateTime(end_dt.year, end_dt.month,
                                           end_dt.day, 0, 0))
         items = items.filter(datetime_received__range=(start_dt, end_dt))
         for chunk in chunkify(items, 10):
             for item in chunk:
                 self.actual_exported_mails += 1
                 logger.error(str(item.datetime_created) + ':' + str(item.subject))
                 skip_list = self.export_item_body(item)
                 attachments += self.export_attachments(item, skip_list)
         self.update_amqp(only_mails=True)
     except ErrorMimeContentConversionFailed:
         msg = '{}: ErrorMimeContentConversionFailed, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))                    
     except ErrorInternalServerError:
         # Possibly happens on p7m files?
         msg = '{}: ErrorInternalServerError, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))
     except ErrorInvalidOperation:
         msg = '{}: ErrorInvalidOperation, giving up sub-folder'
         msg += ' Attachment value: {}'
         logger.warning(msg.format(self.export_path, attachments))
     except ErrorTimeoutExpired:
         attachments = -1
         time.sleep(30)
         logger.warning('{}: ErrorTimeoutExpired'.format(self.export_path))
     except ErrorInternalServerTransientError:
         attachments = -1
         time.sleep(30)
         warning = '{}, {}: ErrorInternalServerTransientError'
         logger.warning(warning.format(self.export_path, folder))
     return attachments
Beispiel #3
0
    def email_scan(self, keyword):

        ##grab login info from config. It's currently reading my email. Should change to a public Phia email account
        config = configparser.ConfigParser()
        config.read('\\\\pgcfpsclrfs\\ClaimDumps\\Bottest\\Python\\config.ini')
        email_username = config.get('Section', 'email_username')
        email_password = config.get('Section', 'email_password')
        email_smtp_address = config.get('Section', 'email_smtp_address')

        keyword = keyword
        credentials = Credentials(username=email_username,
                                  password=email_password)

        account = Account(primary_smtp_address=email_smtp_address,
                          credentials=credentials,
                          autodiscover=True,
                          access_type=DELEGATE)

        ##Grabing date range of this week.
        end = UTC.localize(EWSDateTime.today() + timedelta(days=1))
        lastweek = EWSDateTime.today() - timedelta(days=5)
        start = UTC.localize(lastweek)

        ##Adding the file links from the email into a dictionary.
        dict = {}
        for item in account.inbox.all().filter(
                subject='FW: Scheduled Report Available For Book of Business - Subrogation') \
                .filter(datetime_received__range=(start, end)):

            ##print(item.body)
            soup = BeautifulSoup(item.body, 'lxml')
            for link in soup.findAll('a'):
                newlink = (link.get('href'))
                filtered = soup.find_all(text=re.compile(keyword))
                if 'ReportViewer' in newlink and filtered:

                    datetime = (item.datetime_received)
                    newdict = {newlink: datetime}

                    with open(
                            "\\\\pgcfpsclrfs\\ClaimDumps\\Bottest\\Python\\PythonLog.txt",
                            'w') as f:
                        for key, value in newdict.items():
                            f.write('%s:%s\n' % (key, value))

                    dict.update(newdict)

        return dict
 def total_mails(self):
     """ Return the total amounts of content newet thatn self.start_date
     for the user. This includes mails and calendar items """
     total_count = 0
     if self.account:
         if False:  # TODO: should be if self.start_date
             start_dt = UTC.localize(EWSDateTime(self.start_date.year,
                                                 self.start_date.month,
                                                 self.start_date.day, 0, 0))
             end_dt = UTC.localize(EWSDateTime(2100, 1, 1, 0, 0))
             for folder in self.account.root.walk():
                 items = folder.all()
                 items = items.filter(datetime_received__range=(start_dt,
                                                                end_dt))
                 total_count += items.count()
         else:
             for folder in self.account.root.walk():
                 total_count += folder.total_count
     return total_count
Beispiel #5
0
    def test_naive_datetime(self):
        # Test that we can survive naive datetimes on a datetime field
        tz = EWSTimeZone.timezone('Europe/Copenhagen')
        account = namedtuple('Account',
                             ['default_timezone'])(default_timezone=tz)
        default_value = tz.localize(EWSDateTime(2017, 1, 2, 3, 4))
        field = DateTimeField('foo',
                              field_uri='item:DateTimeSent',
                              default=default_value)

        # TZ-aware datetime string
        payload = b'''\
<?xml version="1.0" encoding="utf-8"?>
<Envelope xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
    <t:Item>
        <t:DateTimeSent>2017-06-21T18:40:02Z</t:DateTimeSent>
    </t:Item>
</Envelope>'''
        elem = to_xml(payload).find('{%s}Item' % TNS)
        self.assertEqual(field.from_xml(elem=elem, account=account),
                         UTC.localize(EWSDateTime(2017, 6, 21, 18, 40, 2)))

        # Naive datetime string is localized to tz of the account
        payload = b'''\
<?xml version="1.0" encoding="utf-8"?>
<Envelope xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
    <t:Item>
        <t:DateTimeSent>2017-06-21T18:40:02</t:DateTimeSent>
    </t:Item>
</Envelope>'''
        elem = to_xml(payload).find('{%s}Item' % TNS)
        self.assertEqual(field.from_xml(elem=elem, account=account),
                         tz.localize(EWSDateTime(2017, 6, 21, 18, 40, 2)))

        # Garbage string returns None
        payload = b'''\
<?xml version="1.0" encoding="utf-8"?>
<Envelope xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
    <t:Item>
        <t:DateTimeSent>THIS_IS_GARBAGE</t:DateTimeSent>
    </t:Item>
</Envelope>'''
        elem = to_xml(payload).find('{%s}Item' % TNS)
        self.assertEqual(field.from_xml(elem=elem, account=account), None)

        # Element not found returns default value
        payload = b'''\
<?xml version="1.0" encoding="utf-8"?>
<Envelope xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
    <t:Item>
    </t:Item>
</Envelope>'''
        elem = to_xml(payload).find('{%s}Item' % TNS)
        self.assertEqual(field.from_xml(elem=elem, account=account),
                         default_value)
Beispiel #6
0
 def test_oof_settings_validation(self):
     with self.assertRaises(ValueError):
         # Needs a start and end
         OofSettings(state=OofSettings.SCHEDULED, ).clean(version=None)
     with self.assertRaises(ValueError):
         # Start must be before end
         OofSettings(
             state=OofSettings.SCHEDULED,
             start=UTC.localize(EWSDateTime(2100, 12, 1)),
             end=UTC.localize(EWSDateTime(2100, 11, 1)),
         ).clean(version=None)
     with self.assertRaises(ValueError):
         # End must be in the future
         OofSettings(
             state=OofSettings.SCHEDULED,
             start=UTC.localize(EWSDateTime(2000, 11, 1)),
             end=UTC.localize(EWSDateTime(2000, 12, 1)),
         ).clean(version=None)
     with self.assertRaises(ValueError):
         # Must have an internal and external reply
         OofSettings(
             state=OofSettings.SCHEDULED,
             start=UTC.localize(EWSDateTime(2100, 11, 1)),
             end=UTC.localize(EWSDateTime(2100, 12, 1)),
         ).clean(version=None)
    def test_ewsdatetime(self):
        # Test a static timezone
        tz = EWSTimeZone.timezone('Etc/GMT-5')
        dt = tz.localize(EWSDateTime(2000, 1, 2, 3, 4, 5))
        self.assertIsInstance(dt, EWSDateTime)
        self.assertIsInstance(dt.tzinfo, EWSTimeZone)
        self.assertEqual(dt.tzinfo.ms_id, tz.ms_id)
        self.assertEqual(dt.tzinfo.ms_name, tz.ms_name)
        self.assertEqual(str(dt), '2000-01-02 03:04:05+05:00')
        self.assertEqual(
            repr(dt),
            "EWSDateTime(2000, 1, 2, 3, 4, 5, tzinfo=<StaticTzInfo 'Etc/GMT-5'>)"
        )

        # Test a DST timezone
        tz = EWSTimeZone.timezone('Europe/Copenhagen')
        dt = tz.localize(EWSDateTime(2000, 1, 2, 3, 4, 5))
        self.assertIsInstance(dt, EWSDateTime)
        self.assertIsInstance(dt.tzinfo, EWSTimeZone)
        self.assertEqual(dt.tzinfo.ms_id, tz.ms_id)
        self.assertEqual(dt.tzinfo.ms_name, tz.ms_name)
        self.assertEqual(str(dt), '2000-01-02 03:04:05+01:00')
        self.assertEqual(
            repr(dt),
            "EWSDateTime(2000, 1, 2, 3, 4, 5, tzinfo=<DstTzInfo 'Europe/Copenhagen' CET+1:00:00 STD>)"
        )

        # Test from_string
        with self.assertRaises(NaiveDateTimeNotAllowed):
            EWSDateTime.from_string('2000-01-02T03:04:05')
        self.assertEqual(EWSDateTime.from_string('2000-01-02T03:04:05+01:00'),
                         UTC.localize(EWSDateTime(2000, 1, 2, 2, 4, 5)))
        self.assertEqual(EWSDateTime.from_string('2000-01-02T03:04:05Z'),
                         UTC.localize(EWSDateTime(2000, 1, 2, 3, 4, 5)))
        self.assertIsInstance(
            EWSDateTime.from_string('2000-01-02T03:04:05+01:00'), EWSDateTime)
        self.assertIsInstance(EWSDateTime.from_string('2000-01-02T03:04:05Z'),
                              EWSDateTime)

        # Test addition, subtraction, summertime etc
        self.assertIsInstance(dt + datetime.timedelta(days=1), EWSDateTime)
        self.assertIsInstance(dt - datetime.timedelta(days=1), EWSDateTime)
        self.assertIsInstance(dt - EWSDateTime.now(tz=tz), datetime.timedelta)
        self.assertIsInstance(EWSDateTime.now(tz=tz), EWSDateTime)
        self.assertEqual(
            dt,
            EWSDateTime.from_datetime(
                tz.localize(datetime.datetime(2000, 1, 2, 3, 4, 5))))
        self.assertEqual(dt.ewsformat(), '2000-01-02T03:04:05+01:00')
        utc_tz = EWSTimeZone.timezone('UTC')
        self.assertEqual(
            dt.astimezone(utc_tz).ewsformat(), '2000-01-02T02:04:05Z')
        # Test summertime
        dt = tz.localize(EWSDateTime(2000, 8, 2, 3, 4, 5))
        self.assertEqual(
            dt.astimezone(utc_tz).ewsformat(), '2000-08-02T01:04:05Z')
        # Test normalize, for completeness
        self.assertEqual(
            tz.normalize(dt).ewsformat(), '2000-08-02T03:04:05+02:00')
        self.assertEqual(
            utc_tz.normalize(dt, is_dst=True).ewsformat(),
            '2000-08-02T01:04:05Z')

        # Test in-place add and subtract
        dt = tz.localize(EWSDateTime(2000, 1, 2, 3, 4, 5))
        dt += datetime.timedelta(days=1)
        self.assertIsInstance(dt, EWSDateTime)
        self.assertEqual(dt, tz.localize(EWSDateTime(2000, 1, 3, 3, 4, 5)))
        dt = tz.localize(EWSDateTime(2000, 1, 2, 3, 4, 5))
        dt -= datetime.timedelta(days=1)
        self.assertIsInstance(dt, EWSDateTime)
        self.assertEqual(dt, tz.localize(EWSDateTime(2000, 1, 1, 3, 4, 5)))

        # Test ewsformat() failure
        dt = EWSDateTime(2000, 1, 2, 3, 4, 5)
        with self.assertRaises(ValueError):
            dt.ewsformat()
        # Test wrong tzinfo type
        with self.assertRaises(ValueError):
            EWSDateTime(2000, 1, 2, 3, 4, 5, tzinfo=pytz.utc)
        with self.assertRaises(ValueError):
            EWSDateTime.from_datetime(EWSDateTime(2000, 1, 2, 3, 4, 5))
Beispiel #8
0
# Datetime math works transparently
two_hours_later = localized_dt + timedelta(hours=2)
two_hours = two_hours_later - localized_dt
two_hours_later += timedelta(hours=2)

# Dates
my_date = EWSDate(2017, 9, 5)
today = EWSDate.today()
also_today = right_now.date()
also_today += timedelta(days=10)

# UTC helpers. 'UTC' is the UTC timezone as an EWSTimeZone instance.
# 'UTC_NOW' returns a timezone-aware UTC timestamp of current time.
from exchangelib import UTC, UTC_NOW

right_now_in_utc = UTC.localize(EWSDateTime.now())
right_now_in_utc = UTC_NOW()

# Already have a Python datetime object you want to use? Make sure it's localized. Then pass
# it to from_datetime().
pytz_tz = pytz.timezone('Europe/Copenhagen')
py_dt = pytz_tz.localize(datetime(2017, 12, 11, 10, 9, 8))
ews_now = EWSDateTime.from_datetime(py_dt)

###Creating, updating, deleting, sending, moving, archiving

# Here's an example of creating a calendar item in the user's standard calendar.  If you want to
# access a non-standard calendar, choose a different one from account.folders[Calendar].
#
# You can create, update and delete single items:
from exchangelib import Account, CalendarItem, Message, Mailbox, FileAttachment, HTMLBody