Библиотека python для использования API Yandex connect / Яндекс коннект.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

499 lines
22 KiB

# coding: utf8
"""
Yandex.Connect Directory API module
:author: Alexeev Nick
:email: n@akolka.ru
:version: 0.2b
"""
from .base import *
from inspect import currentframe
class YandexConnectDirectory(YandexConnectBase):
""" Yandex connect directory API base class """
DOMAIN = u'https://api.directory.yandex.net' # Request Domain
# ------------------------------------------------------------------------------------------------------------------
# Helper functions
# ------------------------------------------------------------------------------------------------------------------
@staticmethod
def prepare_contacts(contacts):
"""
Convert contacts list of tuple to yandex data structure
:param contacts: list[('type', 'value')]
:return: list
"""
if not contacts:
return None
ret = []
if contacts:
for i in range(len(contacts)):
if type(contacts[i]) is tuple:
item = {
"type": contacts[i][0],
"value": contacts[i][1]
}
else:
item = contacts[i]
ret.append(item)
return ret
@staticmethod
def prepare_name(data):
"""
Prepare kwargs name words to yandex data structure
:param data: kwargs of request
:return: None
"""
data['name'] = {
'first': data['name'],
'last': data['secname'],
'middle': data['sername']
}
for key in list(data['name'].keys()):
if not data['name'][key]:
del data['name'][key]
for key in ['secname', 'sername']:
del data[key]
if not data['name']:
del data['name']
# ------------------------------------------------------------------------------------------------------------------
# User
# ------------------------------------------------------------------------------------------------------------------
def user_get_id_by_nickname(self, nickname):
"""
Get user id by nickname
:param nickname: nickname / email
:return: int
"""
if nickname.find('@') > -1:
nickname = nickname[:nickname.find('@')]
if 'user_id_by_email' not in self.cache:
self.cache['user_id_by_email'] = {}
if nickname not in self.cache['user_id_by_email']:
user_items = self.user_list_full(nickname=nickname)
if user_items:
val = user_items[0]['id']
else:
raise YandexConnectException('No found user by nickname "%s"' % nickname)
self.cache['user_id_by_email'][nickname] = val
return self.cache['user_id_by_email'][nickname]
def user_id_check(self, user_id):
"""
Prepare user_id to request
:param user_id: int / str
:return: int
"""
if isinstance(user_id, str):
if not user_id.isdigit():
user_id = self.user_get_id_by_nickname(user_id)
else:
user_id = int(user_id)
return user_id
def user_info(self, user_id, fields=None):
"""
Получение информации о сотруднике
:param user_id: ID
:param fields: поля, по умолчанию: id, nickname
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/read-user-docpage/
:return: yandex request dict — информация о сотруднике
"""
user_id = self.user_id_check(user_id)
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'nickname')
return self.request('users/%s' % user_id, data, method='get')
def user_list(self, fields=None, id=None, nickname=None, department_id=None, recursive_department_id=None, group_id=None, recursive_group_id=None, is_dismissed=None, page=None, per_page=None):
"""
Получение списка сотрудников
:param fields: поля, по умолчанию id, nickname
:param id: фильтр
:param nickname: фильтр
:param department_id: фильтр
:param recursive_department_id: фильтр
:param group_id: фильтр
:param recursive_group_id: фильтр
:param is_dismissed: фильтр
:param page: страница
:param per_page: на странице
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/read-users-list-docpage/
:return: yandex request dict — список сотрудников
"""
group_id = self.group_id_check(group_id)
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'nickname')
return self.request('users', data, method='get')
def user_list_full(self, fields=None, id=None, nickname=None, department_id=None, recursive_department_id=None, group_id=None, recursive_group_id=None, is_dismissed=None):
"""
Получение полного списка сотрудников, без страниц
:param fields: поля, по умолчанию id, nickname
:param id: фильтр
:param nickname: фильтр
:param department_id: фильтр
:param recursive_department_id: фильтр
:param group_id: фильтр
:param recursive_group_id: фильтр
:param is_dismissed: фильтр
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/read-users-list-docpage/
:return: yandex request list - список сотрудников
"""
group_id = self.group_id_check(group_id)
return self.list_full(self.user_list, 'nickname', **inspect_args_func(currentframe()))
def user_add(self, nickname, password, about=None, aliases=None, birthday=None, contacts=None, department_id=1, gender='male', is_admin=None, is_dismissed=None, name=None, secname=None, sername=None, position=None):
"""
Добавление сотрудника
:param nickname: логин
:param password: пароль
:param about: описание
:param aliases: list, ['псевдоним1', ...]
:param birthday: datetime.date, день рождения
:param contacts: list, Контакты в типах яндекса, либо [tuple('type', 'value'), ...]
:param department_id: ID отдела, 1
:param gender: Пол — male|female
:param is_admin: bool, Администор
:param is_dismissed: bool, Увольнение
:param name: Имя
:param secname: Фамилия
:param sername: Отчество
:param position: Должность
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/add-user-docpage/
:return: yandex request dict — созданный сотрудник
"""
data = inspect_args_func(currentframe())
spos = data['nickname'].find('@')
if spos > -1:
data['nickname'] = data['nickname'][:spos]
self.prepare_name(data)
data['contacts'] = self.prepare_contacts(data['contacts'])
return self.request('users', data, method='post')
def user_upd(self, user_id, password=None, about=None, birthday=None, contacts=None, department_id=None, gender=None, is_admin=None, is_dismissed=None, name=None, secname=None, sername=None, position=None, is_enabled=None):
"""
Изменение сотрудника
:param user_id: ID сотрудника
:param password: пароль
:param about: описание
:param aliases: list, ['псевдоним1', ...]
:param birthday: datetime.date, день рождения
:param contacts: list, Контакты в типах яндекса, либо [tuple('type', 'value'), ...]
:param department_id: ID отдела, 1
:param gender: Пол — male|female
:param is_admin: bool, Администор
:param is_dismissed: bool, Увольнение
:param name: Имя
:param secname: Фамилия
:param sername: Отчество
:param position: Должность
:param is_enabled: bool, Блокировка
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/edit-user-docpage/
:return: yandex request dict — измененный сотрудник
"""
user_id = self.user_id_check(user_id)
data = inspect_args_func(currentframe())
self.prepare_name(data)
data['contacts'] = self.prepare_contacts(data['contacts'])
return self.request('users/%s' % user_id, data, method='patch')
def user_alias_add(self, user_id, name):
"""
Добавление алиаса для сотрудника
:param user_id: ID сотрудника
:param name: алиас
:url man: https://tech.yandex.ru/connect/directory/api/concepts/users/add-user-aliases-docpage/
:return: yandex request dict
"""
user_id = self.user_id_check(user_id)
return self.request('users/%s/aliases' % user_id, inspect_args_func(currentframe()), method='post')
# ------------------------------------------------------------------------------------------------------------------
# Department
# ------------------------------------------------------------------------------------------------------------------
def department_list(self, fields=None, page=None, per_page=None):
"""
Получение списка отделов
:param fields: поля, по умолчанию - id, name
:param page: страница
:param per_page: количество элементов на странице
:url man: https://tech.yandex.ru/connect/directory/api/concepts/departments/read-departments-list-docpage/
:return: yandex request list - список отделов
"""
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'name')
return self.request('departments', data, method='get')
def department_list_full(self, fields=None):
"""
Получение полного списка отделов
:param fields: поля, по умолчанию - id, name
:url man: https://tech.yandex.ru/connect/directory/api/concepts/departments/read-departments-list-docpage/
:return: yandex request list - список отделов
"""
return self.list_full(self.department_list, 'name', **inspect_args_func(currentframe()))
def department_info(self, department_id, fields=None):
"""
Получение информации об отделе
:param department_id: ID
:param fields: поля, по умолчанию - id
:return: yandex request dict
"""
return self.request('departments/%s' % department_id, inspect_args_func(currentframe()), method='get')
def department_add(self, name, label, description=None, head_id=None, parent_id=1):
"""
Добавление отдела
:param name: название
:param label: рассылка
:param description: описание
:param head_id: id руководителя отдела
:param parent_id: id родительского отдела, 1
:url man: https://tech.yandex.ru/connect/directory/api/concepts/departments/create-department-docpage/
:return: yandex request dict - созданный отдел
"""
return self.request('departments', inspect_args_func(currentframe()), method='post')
def department_upd(self, department_id, name=None, description=None, head_id=None, label=None, parent_id=None):
"""
Изменение отдела
:param department_id: ID
:param name: название
:param label: рассылка
:param description: описание
:param head_id: id руководителя отдела
:param parent_id: id родительского отдела
:url man: https://tech.yandex.ru/connect/directory/api/concepts/departments/edit-department-docpage/
:return: yandex request dict - созданный отдел
"""
return self.request('departments/%s' % department_id, inspect_args_func(currentframe()), method='patch')
def department_del(self, department_id):
"""
Удаление отдела
:param department_id: ID
:url man: https://tech.yandex.ru/connect/directory/api/concepts/departments/delete-department-docpage/
:return: bool
"""
return self.request('departments/%s' % department_id, method='delete')
# ------------------------------------------------------------------------------------------------------------------
# Group
# ------------------------------------------------------------------------------------------------------------------
def _group_cache_set(self):
"""
Set cache for groups
:return: None
"""
all_groups = self.group_list_full(fields='id,email,name')
self.cache['group_id_by_email'] = {}
self.cache['group_id_by_name'] = {}
for item in all_groups:
self.cache['group_id_by_email'][item['email']] = item['id']
self.cache['group_id_by_name'][item['name']] = item['id']
def group_get_id_by_email(self, email):
"""
Get group ID by email
:param email: email
:return: int
"""
if 'group_id_by_email' not in self.cache:
self._group_cache_set()
if email not in self.cache['group_id_by_email']:
raise YandexConnectException('No found group by email "%s"' % email)
return self.cache['group_id_by_email'][email]
def group_id_check(self, group_id):
"""
Prepare group_id for request
:param group_id: int / str
:return: int
"""
if isinstance(group_id, str):
if group_id.find('@') > -1:
group_id = self.group_get_id_by_email(group_id)
else:
group_id = int(group_id)
return group_id
def group_list(self, fields=None, page=None, per_page=None):
"""
Список команд
:param fields: поля, по умолчанию — id, name
:param page: страница
:param per_page: на странице
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/read-groups-list-docpage/
:return: yandex request list - список команд
"""
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'name')
return self.request('groups', data, method='get')
def group_list_full(self, fields=None):
"""
Полный список команд
:param fields: поля, по умолчанию — id, name, email
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/read-groups-list-docpage/
:return: yandex request list - список команд
"""
if not fields:
fields = ['name', 'email']
return self.list_full(self.group_list, 'name', **inspect_args_func(currentframe()))
def group_info(self, group_id, fields=None):
"""
Получение информации о команде
:param group_id: ID
:param fields: поля, по умолчанию — id, name
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/read-group-docpage/
:return: yandex request dict - команда
"""
group_id = self.group_id_check(group_id)
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'name')
return self.request('groups/%s' % group_id, data, method='get')
def group_add(self, name, label, admins=None, description=None, members=None, type=None):
"""
Добавление команды
:param name: название команды
:param label: название рассылки
:param admins: [{"id": <идентификатор администратора>, "type": "user"},...]
:param description: описание
:param members: list — [{"type": "<user|group|department>", "id": <идентификатор>},...]
:param type: тип - generic|organization_admin|robots|department_head
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/create-group-docpage/
:return: yandex request dict - созданная команда
"""
return self.request('groups', inspect_args_func(currentframe()), method='post')
def group_upd(self, group_id, name=None, label=None, admins=None, description=None, members=None, type=None):
"""
Изменение команды
:param group_id: ID
:param name: название команды
:param label: название рассылки
:param admins: [{"id": <идентификатор администратора>, "type": "user"},...]
:param description: описание
:param members: list — [{"type": "<user|group|department>", "id": <идентификатор>},...]
:param type: тип - generic|organization_admin|robots|department_head
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/edit-group-docpage/
:return: yandex request dict - измененная команда
"""
group_id = self.group_id_check(group_id)
return self.request('groups/%s' % group_id, inspect_args_func(currentframe()), method='patch')
def group_member_list(self, group_id):
"""
Участники команды
:param group_id: ID
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/read-group-members-list-docpage/
:return: yandex request list - участники команды
"""
group_id = self.group_id_check(group_id)
return self.request('groups/%s/members' % group_id, method='get')
def group_member_add(self, group_id, user_id, user_type='user'):
"""
Добавить участника команды
:param group_id: ID | email
:type group_id: int | str
:param user_id: User ID | list | email
:type user_id: int | list | str
:param user_type: Тип - user|group|department
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/add-group-member-docpage/
:return: yandex request dict | list
"""
group_id = self.group_id_check(group_id)
if isinstance(user_id, list):
ret = []
for user_item_id in user_id:
ret.append(self.group_member_add(group_id, user_item_id, user_type=user_type))
return ret
user_id = self.user_id_check(user_id)
data = {
'id': user_id,
'type': user_type
}
return self.request('groups/%s/members' % group_id, data, method='post')
def group_member_del(self, group_id, user_id):
"""
Удалить участника команды
:param group_id: ID
:param user_id: User ID
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/bulk-add-group-member-docpage/
:return: True
"""
group_id = self.group_id_check(group_id)
user_id = self.user_id_check(user_id)
return self.group_member_update(group_id, [{'operation_type': 'remove', 'value': {'id': user_id, 'type': 'user'}}])
def group_member_update(self, group_id, actions):
"""
Изменение участников команды
:param group_id: ID
:param actions: list, [{"operation_type": "<add|remove>", "value": {"type": "<user|group|department>", "id": ID User}},..]
:url man: https://tech.yandex.ru/connect/directory/api/concepts/groups/bulk-add-group-member-docpage/
:return: True
"""
group_id = self.group_id_check(group_id)
return self.request('groups/%s/members/bulk-update' % group_id, data=actions, method='post')
# ------------------------------------------------------------------------------------------------------------------
# Domain
# ------------------------------------------------------------------------------------------------------------------
def domain_list(self, fields=None):
"""
Получение списка доменов
:param fields: поля, по умолчанию name
:url man: https://tech.yandex.ru/connect/directory/api/concepts/domains/read-domains-list-docpage/
:return: yandex request list
"""
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'name', only_title_field=True)
return self.request('domains', data, method='get')
def domain_add(self, name):
"""
Добавить домен
:param name: домен
:url man: https://tech.yandex.ru/connect/directory/api/concepts/domains/add-domain-docpage/
:return: bool
"""
return self.request('domains', inspect_args_func(currentframe()), method='post')
def domain_del(self, name):
"""
Удалить домен
:param name: домен
:url man: https://tech.yandex.ru/connect/directory/api/concepts/domains/delete-domain-docpage/
:return: bool
"""
return self.request('domains/%s' % name, method='delete')
# ------------------------------------------------------------------------------------------------------------------
# Organization
# ------------------------------------------------------------------------------------------------------------------
def organization_list(self, fields=None):
"""
Список организаций
:param fields: поля, по умолчанию — id, name
:return: yandex request list
"""
data = inspect_args_func(currentframe())
data['fields'] = self.prepare_fields(data['fields'], 'name')
return self.request('organizations', data, method='get')['result']