From 750371e595b3007d5c87bc5d8ceadeb02ecc4c3e Mon Sep 17 00:00:00 2001 From: Iurii Tatishchev Date: Tue, 20 Apr 2021 13:29:46 -0700 Subject: [PATCH] move ZendeskAdmin to separate file --- main/extra_func.py | 154 ++++-------------------------------------- main/views.py | 3 +- main/zendesk_admin.py | 138 +++++++++++++++++++++++++++++++++++++ 3 files changed, 153 insertions(+), 142 deletions(-) create mode 100644 main/zendesk_admin.py diff --git a/main/extra_func.py b/main/extra_func.py index 3e54ae4..4aaee13 100644 --- a/main/extra_func.py +++ b/main/extra_func.py @@ -1,5 +1,4 @@ import logging -import os from datetime import timedelta, datetime, date from django.contrib.auth.models import User @@ -7,139 +6,12 @@ from django.core.exceptions import ObjectDoesNotExist from django.utils import timezone from zenpy import Zenpy from zenpy.lib.exception import APIException - +from zenpy.lib.api_objects import User as ZenpyUser from access_controller.settings import ZENDESK_ROLES as ROLES, ONE_DAY, ZENDESK_GROUPS, SOLVED_TICKETS_EMAIL, \ - ACTRL_API_EMAIL, ACTRL_API_TOKEN, ACTRL_API_PASSWORD, ACTRL_ZENDESK_SUBDOMAIN + ACTRL_ZENDESK_SUBDOMAIN from main.models import UserProfile, RoleChangeLogs, UnassignedTicket, UnassignedTicketStatus - - -class ZendeskAdmin: - """ - Класс **ZendeskAdmin** существует, чтобы в каждой функции отдельно не проверять аккаунт администратора. - - :param credentials: Полномочия (первым указывается учетная запись организации в Zendesk) - :type credentials: :class:`dict` - :param email: Email администратора, указанный в env - :type email: :class:`str` - :param token: Токен администратора (формируется в Zendesk, указывается в env) - :type token: :class:`str` - :param password: Пароль администратора, указанный в env - :type password: :class:`str` - """ - - credentials: dict = { - 'subdomain': ACTRL_ZENDESK_SUBDOMAIN - } - email: str = ACTRL_API_EMAIL - token: str = ACTRL_API_TOKEN - password: str = ACTRL_API_PASSWORD - - def __init__(self): - self.create_admin() - - def check_user(self, email: str) -> bool: - """ - Функция осуществляет проверку существования пользователя в Zendesk по email. - - :param email: Email пользователя - :return: Является ли зарегистрированным - """ - return True if self.admin.search(email, type='user') else False - - def get_user_name(self, email: str) -> str: - """ - Функция **get_user_name** возвращает имя пользователя по его email - """ - user = self.admin.users.search(email).values[0] - return user.name - - def get_user_role(self, email: str) -> str: - """ - Функция возвращает роль пользователя по его email. - - :param email: Email пользователя - :return: Роль пользователя - """ - user = self.admin.users.search(email).values[0] - return user.role - - def get_user_id(self, email: str) -> str: - """ - Функция возвращает id пользователя по его email - - :param email: Email пользователя - :return: ID пользователя - """ - user = self.admin.users.search(email).values[0] - return user.id - - def get_user_image(self, email: str) -> str: - """ - Функция возвращает url-ссылку на аватар пользователя по его email. - - :param email: Email пользователя - :return: Аватар пользователя - """ - user = self.admin.users.search(email).values[0] - return user.photo['content_url'] if user.photo else None - - def get_user(self, email: str): - """ - Функция возвращает пользователя (объект) по его email. - - :param email: Email пользователя - :return: Объект пользователя, найденного в БД - """ - return self.admin.users.search(email).values[0] - - def get_group(self, name: str) -> str: - """ - Функция возвращает группу по названию - - :param name: Имя пользователя - :return: Группы пользователя (в случае отсутствия None) - """ - groups = self.admin.search(name, type='group') - for group in groups: - return group - return None - - def get_user_org(self, email: str) -> str: - """ - Функция возвращает организацию, к которой относится пользователь по его email. - - :param email: Email пользователя - :return: Организация пользователя - """ - user = self.admin.users.search(email).values[0] - return user.organization.name if user.organization else None - - def create_admin(self) -> None: - """ - Функция создает администратора, проверяя наличие вводимых данных в env. - - :param credentials: В список полномочий администратора вносятся email, token, password из env - :type credentials: :class:`dict` - :raise: :class:`ValueError`: исключение, вызываемое если email не введен в env - :raise: :class:`APIException`: исключение, вызываемое если пользователя с таким email не существует в Zendesk - """ - - if self.email is None: - raise ValueError('access_controller email not in env') - self.credentials['email'] = self.email - - if self.token: - self.credentials['token'] = self.token - elif self.password: - self.credentials['password'] = self.password - else: - raise ValueError('access_controller token or password not in env') - self.admin = Zenpy(**self.credentials) - try: - self.admin.search(self.email, type='user') - except APIException: - raise ValueError('invalid access_controller`s login data') +from main.zendesk_admin import zenpy def update_role(user_profile: UserProfile, role: int) -> None: @@ -150,7 +22,7 @@ def update_role(user_profile: UserProfile, role: int) -> None: :param role: Новая роль :return: Пользователь с обновленной ролью """ - zendesk = ZendeskAdmin() + zendesk = zenpy user = zendesk.get_user(user_profile.user.email) user.custom_role_id = role user_profile.custom_role_id = role @@ -183,11 +55,11 @@ def make_light_agent(user_profile: UserProfile, who_changes: User) -> None: status=UnassignedTicketStatus.SOLVED if ticket.status == 'solved' else UnassignedTicketStatus.UNASSIGNED ) if ticket.status == 'solved': - ticket.assignee = ZendeskAdmin().get_user(SOLVED_TICKETS_EMAIL) + ticket.assignee = zenpy.get_user(SOLVED_TICKETS_EMAIL) else: ticket.assignee = None - ticket.group = ZendeskAdmin().get_group(ZENDESK_GROUPS['buffer']) - ZendeskAdmin().admin.tickets.update(ticket) + ticket.group = zenpy.get_group(ZENDESK_GROUPS['buffer']) + zenpy.admin.tickets.update(ticket) update_role(user_profile, ROLES['light_agent']) @@ -195,7 +67,7 @@ def get_users_list() -> list: """ Функция **get_users_list** возвращает список пользователей Zendesk, относящихся к организации SYSTEM. """ - zendesk = ZendeskAdmin() + zendesk = zenpy # У пользователей должна быть организация SYSTEM org = next(zendesk.admin.search(type='organization', name='SYSTEM')) @@ -207,7 +79,7 @@ def get_tickets_list(email): """ Функция возвращает список тикетов пользователя Zendesk """ - return ZendeskAdmin().admin.search(assignee=email, type='ticket') + return zenpy.admin.search(assignee=email, type='ticket') def update_profile(user_profile: UserProfile) -> UserProfile: @@ -217,7 +89,7 @@ def update_profile(user_profile: UserProfile) -> UserProfile: :param user_profile: Профиль пользователя :return: Обновленный, в соответствие с текущими данными в Zendesk, профиль пользователя """ - user = ZendeskAdmin().get_user(user_profile.user.email) + user = zenpy.get_user(user_profile.user.email) user_profile.name = user.name user_profile.role = user.role user_profile.custom_role_id = user.custom_role_id if user.custom_role_id else 0 @@ -232,7 +104,7 @@ def check_user_exist(email: str) -> bool: :param email: Email пользователя :return: Зарегистрирован ли пользователь в Zendesk """ - return ZendeskAdmin().check_user(email) + return zenpy.check_user(email) def get_user_organization(email: str) -> str: @@ -242,7 +114,7 @@ def get_user_organization(email: str) -> str: :param email: Email пользователя :return: Организация пользователя """ - return ZendeskAdmin().get_user_org(email) + return zenpy.get_user_org(email) def check_user_auth(email: str, password: str) -> bool: @@ -264,7 +136,7 @@ def check_user_auth(email: str, password: str) -> bool: return True -def update_user_in_model(profile: UserProfile, zendesk_user: User): +def update_user_in_model(profile: UserProfile, zendesk_user: ZenpyUser): """ Функция обновляет профиль пользователя при изменении данных пользователя на Zendesk. diff --git a/main/views.py b/main/views.py index 0c89f11..c7eec58 100644 --- a/main/views.py +++ b/main/views.py @@ -23,7 +23,8 @@ from zenpy.lib.api_objects import User as ZenpyUser from access_controller.settings import DEFAULT_FROM_EMAIL, ZENDESK_ROLES, ZENDESK_MAX_AGENTS from main.extra_func import check_user_exist, update_profile, get_user_organization, \ make_engineer, make_light_agent, get_users_list, update_users_in_model, count_users, \ - StatisticData, log, ZendeskAdmin + StatisticData, log +from main.zendesk_admin import ZendeskAdmin from main.forms import AdminPageUsers, CustomRegistrationForm, CustomAuthenticationForm, StatisticForm from main.serializers import ProfileSerializer, ZendeskUserSerializer from .models import UserProfile diff --git a/main/zendesk_admin.py b/main/zendesk_admin.py new file mode 100644 index 0000000..e0d1674 --- /dev/null +++ b/main/zendesk_admin.py @@ -0,0 +1,138 @@ +from typing import Optional + +from zenpy import Zenpy +from zenpy.lib.api_objects import User as ZenpyUser +from zenpy.lib.exception import APIException + +from access_controller.settings import ACTRL_ZENDESK_SUBDOMAIN, ACTRL_API_EMAIL, ACTRL_API_TOKEN, ACTRL_API_PASSWORD + + +class ZendeskAdmin: + """ + Класс **ZendeskAdmin** существует, чтобы в каждой функции отдельно не проверять аккаунт администратора. + + :param credentials: Полномочия (первым указывается учетная запись организации в Zendesk) + :type credentials: :class:`dict` + :param email: Email администратора, указанный в env + :type email: :class:`str` + :param token: Токен администратора (формируется в Zendesk, указывается в env) + :type token: :class:`str` + :param password: Пароль администратора, указанный в env + :type password: :class:`str` + """ + + credentials: dict = { + 'subdomain': ACTRL_ZENDESK_SUBDOMAIN + } + email: str = ACTRL_API_EMAIL + token: str = ACTRL_API_TOKEN + password: str = ACTRL_API_PASSWORD + + def __init__(self): + self.create_admin() + + def check_user(self, email: str) -> bool: + """ + Функция осуществляет проверку существования пользователя в Zendesk по email. + + :param email: Email пользователя + :return: Является ли зарегистрированным + """ + return True if self.admin.search(email, type='user') else False + + def get_user_name(self, email: str) -> str: + """ + Функция **get_user_name** возвращает имя пользователя по его email + """ + user = self.admin.users.search(email).values[0] + return user.name + + def get_user_role(self, email: str) -> str: + """ + Функция возвращает роль пользователя по его email. + + :param email: Email пользователя + :return: Роль пользователя + """ + user = self.admin.users.search(email).values[0] + return user.role + + def get_user_id(self, email: str) -> str: + """ + Функция возвращает id пользователя по его email + + :param email: Email пользователя + :return: ID пользователя + """ + user = self.admin.users.search(email).values[0] + return user.id + + def get_user_image(self, email: str) -> str: + """ + Функция возвращает url-ссылку на аватар пользователя по его email. + + :param email: Email пользователя + :return: Аватар пользователя + """ + user = self.admin.users.search(email).values[0] + return user.photo['content_url'] if user.photo else None + + def get_user(self, email: str) -> ZenpyUser: + """ + Функция возвращает пользователя (объект) по его email. + + :param email: Email пользователя + :return: Объект пользователя, найденного в БД + """ + return self.admin.users.search(email).values[0] + + def get_group(self, name: str) -> Optional[str]: + """ + Функция возвращает группу по названию + + :param name: Имя пользователя + :return: Группы пользователя (в случае отсутствия None) + """ + groups = self.admin.search(name, type='group') + for group in groups: + return group + return None + + def get_user_org(self, email: str) -> str: + """ + Функция возвращает организацию, к которой относится пользователь по его email. + + :param email: Email пользователя + :return: Организация пользователя + """ + user = self.admin.users.search(email).values[0] + return user.organization.name if user.organization else None + + def create_admin(self) -> None: + """ + Функция создает администратора, проверяя наличие вводимых данных в env. + + :param credentials: В список полномочий администратора вносятся email, token, password из env + :type credentials: :class:`dict` + :raise: :class:`ValueError`: исключение, вызываемое если email не введен в env + :raise: :class:`APIException`: исключение, вызываемое если пользователя с таким email не существует в Zendesk + """ + + if self.email is None: + raise ValueError('access_controller email not in env') + self.credentials['email'] = self.email + + if self.token: + self.credentials['token'] = self.token + elif self.password: + self.credentials['password'] = self.password + else: + raise ValueError('access_controller token or password not in env') + self.admin = Zenpy(**self.credentials) + try: + self.admin.search(self.email, type='user') + except APIException: + raise ValueError('invalid access_controller`s login data') + + +zenpy = ZendeskAdmin()