ees_microsoft_teams/microsoft_teams_calendars.py (98 lines of code) (raw):

# # Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one # or more contributor license agreements. Licensed under the Elastic License 2.0; # you may not use this file except in compliance with the Elastic License 2.0. # """ This module fetches all calendars events from Microsoft Teams. """ from calendar import month_name from collections import defaultdict from datetime import datetime from . import constant from .microsoft_teams_client import MSTeamsClient from .microsoft_teams_users import MSTeamsUsers from .utils import get_schema_fields USER_MEETING_DATETIME_FORMAT = "%Y-%m-%dT%H:%M:%S.%f" MEETING = "Meeting" class MSTeamsCalendar: """Fetches calendars for all users from Microsoft Teams""" def __init__(self, access_token, logger, config, local_storage): self.token = access_token self.local_storage = local_storage self.client = MSTeamsClient(logger, self.token, config) self.users_obj = MSTeamsUsers(self.token, logger) self.logger = logger self.config = config self.object_type_to_index = config.get_value('object_type_to_index') def get_calendar_detail(self, attendees, calendar): """This method is used to fetch the calendar details for creating body in the workplace :param attendees: All the attendees seprated by comma :param calendar: Dictionary of event details Returns: body: body with event details which going to be indexed in Workplace Search """ body = '' if calendar['recurrence']: range = calendar['recurrence']['range'] pattern = calendar['recurrence']['pattern'] occurrence = f"{pattern['interval']}" if pattern['interval'] else "" # In case type of meeting is daily so body will be: Recurrence: Occurs every 1 day starting {startdate} # until {enddate} if pattern['type'] == 'daily': days = f"{occurrence} day" # If type of meeting is yearly so body will be: Recurrence: Occurs every year on day 5 of march starting # {date} until {enddate} elif pattern['type'] in ['absoluteYearly', 'relativeYearly']: day_pattern = f"on day {pattern['dayOfMonth']}" if pattern['dayOfMonth'] else "on " \ f"{pattern['index']} {','.join(pattern['daysOfWeek'])}" days = f"year {day_pattern} of {month_name[pattern['month']]}" # If type of meeting is monthly so body will be: Recurrence: Occurs every month on day 5 of march # starting {date} until {enddate} elif pattern['type'] in ['absoluteMonthly', 'relativeMonthly']: days_pattern = f"on day {pattern['dayOfMonth']}" if pattern['dayOfMonth'] else f"on " \ f"{pattern['index']} {','.join(pattern['daysOfWeek'])}" days = f"{occurrence} month {days_pattern}" # Else goes in weekly situation where body will be: Recurrence: Occurs Every 3 week on monday,tuesday, # wednesday starting {date} until {enddate} else: week = ','.join(pattern['daysOfWeek']) days = f"{occurrence} week on {week}" date = f"{range['startDate']}" if range['type'] == 'noEnd' else f"{range['startDate']} until " \ f"{range['endDate']}" recurrance = f"Occurs Every {days} starting {date}" body = f'Recurrence: {recurrance} \nOrganizer: {calendar["organizer"]["emailAddress"]["name"]} ' \ f'\nAttendees: {attendees} \nDescription: {calendar["bodyPreview"]}' else: start_time = datetime.strptime(calendar["start"]["dateTime"][: -4], USER_MEETING_DATETIME_FORMAT).strftime( "%d %b, %Y at %H:%M") end_time = datetime.strptime(calendar["end"]["dateTime"][: -4], USER_MEETING_DATETIME_FORMAT).strftime( "%d %b, %Y at %H:%M") body = f'Schedule: {start_time} to {end_time} \nOrganizer: ' \ f'{calendar["organizer"]["emailAddress"]["name"]} \nAttendees: {attendees} \nDescription: ' \ f'{calendar["bodyPreview"]}' return body def get_calendars(self, ids_list, start_time, end_time): """ Fetches all calendar events from Microsoft Teams. :param ids_list: List of ids Returns: permissions_dict: List of dictionaries containing calendar id and their members documents: Documents to be indexed in Workplace Search """ self.logger.debug("Fetching users for Calendar Events") users = self.users_obj.get_all_users() self.logger.info("Fetched the users metadata. Attempting to extract the meetings from the calendar...") documents = [] permissions_dict = defaultdict(list) calendar_schema = get_schema_fields("calendar", self.object_type_to_index) for user in users: # Logic to append calendar for deletion self.local_storage.insert_document_into_doc_id_storage(ids_list, user["userId"], constant.USER, "", "") try: response = self.client.get_calendars( next_url=f'{constant.GRAPH_BASE_URL}/users/{user["userId"]}/events', start_time=start_time, end_time=end_time ) if not response: continue for calendar in response: if not calendar['isCancelled']: # Logic to append calendar for deletion self.local_storage.insert_document_into_doc_id_storage( ids_list, calendar["id"], constant.CALENDAR, user["userId"], "" ) calendar_dict = {"type": MEETING} permissions_dict[user["displayName"]].append(calendar["id"]) attendee_list = [] for att in calendar['attendees']: attendee_list.append(f"{att['emailAddress']['name']}" f"({att['emailAddress']['address']})") attendees = ",".join(attendee_list) body = self.get_calendar_detail(attendees, calendar) for ws_field, ms_fields in calendar_schema.items(): calendar_dict[ws_field] = calendar[ms_fields] calendar_dict['body'] = body if calendar['onlineMeeting']: calendar_dict['url'] = calendar["onlineMeeting"]['joinUrl'] calendar_dict["_allow_permissions"] = [] if self.config.get_value("enable_document_permission"): calendar_dict["_allow_permissions"] = [calendar['id']] documents.append(calendar_dict) except Exception as exception: self.logger.exception(f"Error while fetching the calendar events from teams. Error: {exception}") raise exception return permissions_dict, documents