class ZendeskConnector(BaseConnection): def __init__(self, connector): self.connector = connector self.settings = frappe.get_doc("Zendesk Settings", None) if not self.settings.last_user_sync: frappe.db.set_value("Zendesk Settings", None, "last_user_sync", now_datetime()) if not self.settings.last_org_sync: frappe.db.set_value("Zendesk Settings", None, "last_org_sync", now_datetime()) self.name_field = 'id' try: self.zenpy_client = Zenpy(**{ 'email' : self.settings.email, 'token' : self.settings.get_password(fieldname='api_token',raise_exception=False), 'subdomain': self.settings.subdomain }) except Exception as e: frappe.log_error(e, 'Zendesk Connection Error') try: found = False if self.settings.org_type_id: for field in self.zenpy_client.organization_fields(): if field.id == self.settings.org_type_id: found = True if found == False: for field in self.zenpy_client.organization_fields(): if field.key == 'is_supplier' and field.type == 'checkbox': frappe.db.set_value("Zendesk Settings", "Zendesk Settings", "org_type_id", field.id) found = True if found == False: self.create_custom_field() else: for field in self.zenpy_client.organization_fields(): if field.key == 'is_supplier' and field.type == 'checkbox': frappe.db.set_value("Zendesk Settings", "Zendesk Settings", "org_type_id", field.id) found = True if found == False: self.create_custom_field() except Exception as e: frappe.log_error(e, 'Zendesk Setup Error') def create_custom_field(self, id=None): custom_field = OrganizationField(type="checkbox", title="Is a supplier", key="is_supplier", raw_title="Is a supplier") try: self.zenpy_client.organization_fields.create(custom_field) except Exception as e: frappe.log_error(e, 'Zendesk custom field creation error') def get(self, remote_objectname, fields=None, filters=None, start=0, page_length=10): search = filters.get('search') organization_type = filters.get('organization_type') export_type = filters.get('export_type') if remote_objectname == 'User': if export_type == "incremental": try: return self.get_incremental_users(search, start, page_length) except Exception as e: frappe.log_error(e, 'Zendesk Contact Get Error') else: try: return self.get_users(search, start, page_length) except Exception as e: frappe.log_error(e, 'Zendesk Contact Get Error') if remote_objectname == 'Organization': if export_type == "incremental": try: return self.get_incremental_organizations(search, organization_type, start, page_length) except Exception as e: frappe.log_error(e, 'Zendesk Company Get Error') else: try: return self.get_organizations(search, organization_type, start, page_length) except Exception as e: frappe.log_error(e, 'Zendesk Company Get Error') def insert(self, doctype, doc): if doctype == 'User': try: return self.insert_users(doc) except Exception as e: return frappe.log_error("Doc {0}: {1}".format(doc, e), 'Zendesk Contact Insert Error') if doctype == 'Organization': try: return self.insert_organizations(doc) except Exception as e: return frappe.log_error("Doc {0}: {1}".format(doc, e), 'Zendesk Organization Insert Error') def update(self, doctype, doc, migration_id): if doctype == 'User': try: return self.update_users(doc, migration_id) except Exception as e: frappe.log_error("Doc {0}: {1}".format(doc, e), 'Zendesk Contact Update Error') if doctype == 'Organization': try: return self.update_organizations(doc, migration_id) except Exception as e: frappe.log_error("Doc {0}: {1}".format(doc, e), 'Zendesk Company Update Error') def delete(self, doctype, migration_id): pass def get_users(self, search, start=0, page_length=100): users = self.zenpy_client.users() result = [] for user in users: result.append(user) return list(result) def get_incremental_users(self, search, start=0, page_length=100): users = self.zenpy_client.users.incremental(start_time=get_datetime(self.settings.last_user_sync)) result = [] for user in users: result.append(user) frappe.db.set_value("Zendesk Settings", None, "last_user_sync", now_datetime()) return list(result) def get_organizations(self, search, organization_type, start=0, page_length=100): organizations = self.zenpy_client.organizations() result = [] for org in organizations: if organization_type == "customer": if not org.organization_fields["is_supplier"] or org.organization_fields["is_supplier"] == False: result.append(org) else: if org.organization_fields["is_supplier"] == True: result.append(org) return list(result) def get_incremental_organizations(self, search, organization_type, start=0, page_length=100): organizations = self.zenpy_client.organizations.incremental(start_time=get_datetime(self.settings.last_org_sync)) result = [] for org in organizations: if organization_type == "customer": if not org.organization_fields["is_supplier"] or org.organization_fields["is_supplier"] == False: result.append(org) else: if org.organization_fields["is_supplier"] == True: result.append(org) if organization_type == "supplier": frappe.db.set_value("Zendesk Settings", None, "last_org_sync", now_datetime()) return list(result) def insert_users(self, doc): user = User( id=doc.id, name=doc.name, email=doc.email, phone=doc.phone, organization_id=doc.organization_id ) created_user = self.zenpy_client.users.create(user) if hasattr(created_user, "error"): frappe.log_error("Doc {0}: {1}".format(doc, created_user.description), "Zendesk Contact Insert Response Error") else: return {self.name_field: created_user.id} def insert_organizations(self, doc): if hasattr(doc, "organization_fields"): organization = Organization(name=doc.name, organization_fields=doc.organization_fields) else: organization = Organization(name=doc.name) created_organization = self.zenpy_client.organizations.create(organization) if hasattr(created_organization, "error"): frappe.log_error("Doc {0}: {1}".format(doc, created_organization.description), "Zendesk Companies Insert Error") else: return {self.name_field: created_organization.id} def update_users(self, doc, migration_id): user = User( id=doc.id, name=doc.name, email=doc.email, phone=doc.name, organization_id=doc.organization_id ) updated_user = self.zenpy_client.users.create_or_update(user) if hasattr(updated_user, "error"): frappe.log_error("Id {0}: {1}".format(migration_id, updated_user.description), "Zendesk Contact Update Error") else: return {self.name_field: updated_user.id} def update_organizations(self, doc, migration_id): organization = Organization(id=doc.id, name=doc.name, organization_fields=doc.organization_fields) updated_organization = self.zenpy_client.organizations.update(organization) if hasattr(updated_organization, "error"): frappe.log_error("Id {0}: {1}".format(migration_id, updated_organization.description), "Zendesk Company Update Error") else: return {self.name_field: updated_organization.id}
class ZendeskMetrics: def __init__(self, user, token, NoOfdays): self.creds = {'email': user, 'token': token, 'subdomain': 'qubole'} self.client = Zenpy(**self.creds) self.startTime = datetime.datetime.now() - datetime.timedelta( days=NoOfdays) self.result_generator = self.client.tickets.incremental( start_time=self.startTime) # Create Schema for the table def CreateSchema(self): Custom_Field_Names = [] i = 1 SampleInterval = datetime.datetime.now() - datetime.timedelta(days=1) sample_result = self.client.tickets.incremental( start_time=SampleInterval) for ticket in sample_result: Custom_Fields = ticket.custom_fields for dictItem in Custom_Fields: if str(dictItem['id']) not in ("24720303", "22165409", "22214565", "22165259"): checkCustomField = str( dictItem['id']) in Custom_Field_Values if checkCustomField: Custom_Field_Names.append(Custom_Field_Values[str( dictItem['id'])]) else: Custom_Field_Names.append("New Field " + str(i)) i = i + 1 break self.Table_Schema = [ 'Ticket_Id', 'Ticket_Subject', 'Ticket_Status', 'Assignee', 'Requester', 'Organization', 'Priority' ] + Custom_Field_Names + ['Created_At', 'Last_Updated_At'] return self.Table_Schema # Convert String to DataTime Object def ConvertStrToDatetime(self, DateStr): StripDate = DateStr.replace('T', ' ').replace('Z', '') #print(StripDate) self.DateForm = datetime.datetime.strptime(StripDate, '%Y-%m-%d %H:%M:%S') #print(DateForm) return self.DateForm # Fetch Data using zenpy api def CollectMetrics(self): self.All_Tickets = [] for ticket in self.result_generator: ticket_details = [] try: ticket_details.append(ticket.id) except: ticket_details.append(00000) try: ticket_details.append(ticket.subject) except: ticket_details.append('Subject Missing') try: ticket_details.append(ticket.status) except: ticket_details.append('Status Missing') try: ticket_details.append( self.client.users(id=ticket.assignee_id).name) except: ticket_details.append('Unassigned') try: ticket_details.append( self.client.users(id=ticket.requester_id).name) except: ticket_details.append('Unknown') try: ticket_details.append( self.client.organizations(id=ticket.organization_id).name) except: ticket_details.append('Unknown') try: ticket_details.append(ticket.priority) except: ticket_details.append('Unknown') # Fetch data from the custom fields List_custom_Fields = ticket.custom_fields for dictItem in List_custom_Fields: if str(dictItem['id']) not in ("24720303", "22165409", "22214565", "22165259"): if str(dictItem['id']) == "24720283": try: ticket_details.append(int(dictItem['value'])) except: ticket_details.append(0) continue if str(dictItem['value']) == "None": dictItem['value'] = "" try: ticket_details.append(str(dictItem['value'])) except: ticket_details.append('') CreatedAtDate = self.ConvertStrToDatetime(ticket.created_at) try: ticket_details.append(CreatedAtDate) except: ticket_details.append(datetime.datetime( 1971, 1, 1, 0, 0, 0)) # For the missing Created_at date UpdatedAtDate = self.ConvertStrToDatetime(ticket.updated_at) try: ticket_details.append(UpdatedAtDate) except: ticket_details.append(datetime.datetime( 1971, 1, 1, 0, 0, 0)) # for the missing Updated_at date self.All_Tickets.append(ticket_details) return self.All_Tickets # This function is to create Pandas DataFrame def CreatePandasDF(self, All_Tickets, Schema): df = pd.DataFrame(self.All_Tickets, columns=Schema) return df