Browse Source

Add support for bot integrations

pull/6987/head
Maya 4 years ago
committed by GitHub
parent
commit
4d7822493f
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 11
      discord/guild.py
  2. 216
      discord/integrations.py
  3. 9
      docs/api.rst

11
discord/guild.py

@ -45,7 +45,7 @@ from .iterators import AuditLogIterator, MemberIterator
from .widget import Widget
from .asset import Asset
from .flags import SystemChannelFlags
from .integrations import Integration
from .integrations import BotIntegration, StreamIntegration, _integration_factory
__all__ = (
'Guild',
@ -1803,7 +1803,14 @@ class Guild(Hashable):
The list of integrations that are attached to the guild.
"""
data = await self._state.http.get_all_integrations(self.id)
return [Integration(guild=self, data=d) for d in data]
def convert(d):
factory, itype = _integration_factory(d['type'])
if factory is None:
raise InvalidData('Unknown integration type {type!r} for integration ID {id}'.format_map(d))
return factory(guild=self, data=d)
return [convert(d) for d in data]
async def fetch_emojis(self):
r"""|coro|

216
discord/integrations.py

@ -27,19 +27,25 @@ from __future__ import annotations
import datetime
from typing import Optional, TYPE_CHECKING, overload
from .utils import _get_as_snowflake, get, parse_time
from .role import Role
from .user import User
from .errors import InvalidArgument
from .enums import try_enum, ExpireBehaviour
__all__ = (
'IntegrationAccount',
'IntegrationApplication',
'Integration',
'StreamIntegration',
'BotIntegration',
)
if TYPE_CHECKING:
from .types.integration import (
IntegrationAccount as IntegrationAccountPayload,
Integration as IntegrationPayload,
IntegrationType,
IntegrationApplication as IntegrationApplicationPayload,
)
from .guild import Guild
@ -74,6 +80,75 @@ class Integration:
Attributes
-----------
id: :class:`int`
The integration ID.
name: :class:`str`
The integration name.
guild: :class:`Guild`
The guild of the integration.
type: :class:`str`
The integration type (i.e. Twitch).
enabled: :class:`bool`
Whether the integration is currently enabled.
account: :class:`IntegrationAccount`
The account linked to this integration.
user: :class:`User`
The user that added this integration.
"""
__slots__ = (
'guild',
'id',
'_state',
'type',
'name',
'account',
'user',
'enabled',
)
def __init__(self, *, data: IntegrationPayload, guild: Guild) -> None:
self.guild = guild
self._state = guild._state
self._from_data(data)
def __repr__(self):
return f"<{self.__class__.__name__} id={self.id} name={self.name!r}>"
def _from_data(self, data: IntegrationPayload) -> None:
self.id: int = int(data['id'])
self.type: IntegrationType = data['type']
self.name: str = data['name']
self.account: IntegrationAccount = IntegrationAccount(data['account'])
user = data.get('user')
self.user = User(state=self._state, data=user) if user else None
self.enabled: bool = data['enabled']
async def delete(self) -> None:
"""|coro|
Deletes the integration.
You must have the :attr:`~Permissions.manage_guild` permission to
do this.
Raises
-------
Forbidden
You do not have permission to delete the integration.
HTTPException
Deleting the integration failed.
"""
await self._state.http.delete_integration(self.guild.id, self.id)
class StreamIntegration(Integration):
"""Represents a stream integration for Twitch or YouTube.
.. versionadded:: 2.0
Attributes
----------
id: :class:`int`
The integration ID.
name: :class:`str`
@ -102,49 +177,30 @@ class Integration:
An aware UTC datetime representing when the integration was last synced.
"""
__slots__ = (
'id',
'_state',
'guild',
'name',
'enabled',
'type',
'syncing',
'role',
__slots__ = Integration.__slots__ + (
'revoked',
'expire_behaviour',
'expire_behavior',
'expire_grace_period',
'synced_at',
'user',
'account',
'enable_emoticons',
'_role_id',
'role',
'syncing',
'enable_emoticons',
'subscriber_count'
)
def __init__(self, *, data: IntegrationPayload, guild: Guild) -> None:
self.guild = guild
self._state = guild._state
self._from_data(data)
def __repr__(self) -> str:
return f'<Integration id={self.id} name={self.name!r} type={self.type!r}>'
def _from_data(self, integ: IntegrationPayload):
self.id = _get_as_snowflake(integ, 'id')
self.name = integ['name']
self.type = integ['type']
self.enabled = integ['enabled']
self.syncing = integ['syncing']
self._role_id = _get_as_snowflake(integ, 'role_id')
self.role = get(self.guild.roles, id=self._role_id)
self.enable_emoticons = integ.get('enable_emoticons')
self.expire_behaviour = try_enum(ExpireBehaviour, integ['expire_behavior'])
self.expire_behavior = self.expire_behaviour
self.expire_grace_period = integ['expire_grace_period']
self.synced_at = parse_time(integ['synced_at'])
self.user = User(state=self._state, data=integ['user'])
self.account = IntegrationAccount(integ['account'])
def _from_data(self, data: IntegrationPayload) -> None:
super()._from_data(data)
self.revoked: bool = data['revoked']
self.expire_behaviour: ExpireBehaviour = try_enum(ExpireBehaviour, data['expire_behavior'])
self.expire_grace_period: int = data['expire_grace_period']
self.synced_at: datetime.datetime = parse_time(data['synced_at'])
self._role_id: int = int(data['role_id'])
self.role: Role = self.guild.get_role(self._role_id)
self.syncing: bool = data['syncing']
self.enable_emoticons: bool = data['enable_emoticons']
self.subscriber_count: int = data['subscriber_count']
@overload
async def edit(
@ -231,19 +287,81 @@ class Integration:
await self._state.http.sync_integration(self.guild.id, self.id)
self.synced_at = datetime.datetime.now(datetime.timezone.utc)
async def delete(self) -> None:
"""|coro|
class IntegrationApplication:
"""Represents an application for a bot integration.
Deletes the integration.
.. versionadded:: 2.0
You must have the :attr:`~Permissions.manage_guild` permission to
do this.
Attributes
----------
id: :class:`int`
The ID for this application.
name: :class:`str`
The application's name.
icon: Optional[:class:`str`]
The application's icon hash.
description: :class:`str`
The application's description. Can be an empty string.
summary: :class:`str`
The summary of the application. Can be an empty string.
user: Optional[:class:`User`]
The bot user on this application.
"""
Raises
-------
Forbidden
You do not have permission to delete the integration.
HTTPException
Deleting the integration failed.
"""
await self._state.http.delete_integration(self.guild.id, self.id)
__slots__ = (
'id',
'name',
'icon',
'description',
'summary',
'user',
)
def __init__(self, *, data: IntegrationApplicationPayload, state):
self.id: int = int(data['id'])
self.name: str = data['name']
self.icon: Optional[str] = data['icon']
self.description: str = data['description']
self.summary: str = data['summary']
user = data.get('bot')
self.user: Optional[User] = User(state=state, data=user) if user else None
class BotIntegration(Integration):
"""Represents a bot integration on discord.
.. versionadded:: 2.0
Attributes
----------
id: :class:`int`
The integration ID.
name: :class:`str`
The integration name.
guild: :class:`Guild`
The guild of the integration.
type: :class:`str`
The integration type (i.e. Twitch).
enabled: :class:`bool`
Whether the integration is currently enabled.
user: :class:`User`
The user that added this integration.
account: :class:`IntegrationAccount`
The integration account information.
application: :class:`IntegrationApplication`
The application tied to this integration.
"""
__slots__ = Integration.__slots__ + ('application',)
def _from_data(self, data: IntegrationPayload) -> None:
super()._from_data(data)
self.application = IntegrationApplication(data=data['application'], state=self._state)
def _integration_factory(value):
if value == 'discord':
return BotIntegration, value
elif value in ('twitch', 'youtube'):
return StreamIntegration, value
else:
return Integration, value

9
docs/api.rst

@ -2986,6 +2986,15 @@ Integration
.. autoclass:: IntegrationAccount()
:members:
.. autoclass:: BotIntegration()
:members:
.. autoclass:: IntegrationApplication()
:members:
.. autoclass:: StreamIntegration()
:members:
Interaction
~~~~~~~~~~~~

Loading…
Cancel
Save