Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for getting and editing integration_types_config application field #9818

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
125 changes: 124 additions & 1 deletion discord/appinfo.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@

from __future__ import annotations

from typing import List, TYPE_CHECKING, Optional
from typing import List, TYPE_CHECKING, Literal, Optional

from . import utils
from .asset import Asset
Expand All @@ -41,6 +41,7 @@
PartialAppInfo as PartialAppInfoPayload,
Team as TeamPayload,
InstallParams as InstallParamsPayload,
AppIntegrationTypeConfig as AppIntegrationTypeConfigPayload,
)
from .user import User
from .state import ConnectionState
Expand All @@ -49,6 +50,7 @@
'AppInfo',
'PartialAppInfo',
'AppInstallParams',
'IntegrationTypeConfig',
)


Expand Down Expand Up @@ -180,6 +182,7 @@
'redirect_uris',
'approximate_guild_count',
'approximate_user_install_count',
'_integration_types_config',
)

def __init__(self, state: ConnectionState, data: AppInfoPayload):
Expand Down Expand Up @@ -218,6 +221,9 @@
self.redirect_uris: List[str] = data.get('redirect_uris', [])
self.approximate_guild_count: int = data.get('approximate_guild_count', 0)
self.approximate_user_install_count: Optional[int] = data.get('approximate_user_install_count')
self._integration_types_config: Dict[Literal["0", "1"], AppIntegrationTypeConfigPayload] = data.get(
'integration_types_config', {}
)

def __repr__(self) -> str:
return (
Expand Down Expand Up @@ -260,6 +266,36 @@
"""
return ApplicationFlags._from_value(self._flags)

@property
def guild_integration_config(self) -> Optional[IntegrationTypeConfig]:
"""Optional[:class:`IntegrationTypeConfig`]: The default settings for the
application's installation context in a guild.

.. versionadded:: 2.5
"""
if not self._integration_types_config:
return None

try:
return IntegrationTypeConfig(self._integration_types_config['0'])
except KeyError:
return None

@property
def user_integration_config(self) -> Optional[IntegrationTypeConfig]:
"""Optional[:class:`IntegrationTypeConfig`]: The default settings for the
application's installation context as a user.

.. versionadded:: 2.5
"""
if not self._integration_types_config:
return None

try:
return IntegrationTypeConfig(self._integration_types_config['1'])
except KeyError:
return None

async def edit(
self,
*,
Expand All @@ -274,6 +310,10 @@
cover_image: Optional[bytes] = MISSING,
interactions_endpoint_url: Optional[str] = MISSING,
tags: Optional[List[str]] = MISSING,
guild_install_scopes: Optional[List[str]] = MISSING,
guild_install_permissions: Optional[Permissions] = MISSING,
user_install_scopes: Optional[List[str]] = MISSING,
user_install_permissions: Optional[Permissions] = MISSING,
) -> AppInfo:
r"""|coro|

Expand Down Expand Up @@ -315,6 +355,24 @@
over the gateway. Can be ``None`` to remove the URL.
tags: Optional[List[:class:`str`]]
The new list of tags describing the functionality of the application. Can be ``None`` to remove the tags.
guild_install_scopes: Optional[List[:class:`str`]]
The new list of :ddocs:`OAuth2 scopes <topics/oauth2#shared-resources-oauth2-scopes>` of
the default guild installation context. Can be ``None`` to remove the scopes.

.. versionadded: 2.5
guild_install_permissions: Optional[:class:`Permissions`]
The new permissions of the default guild installation context. Can be ``None`` to remove the permissions.

.. versionadded: 2.5
user_install_scopes: Optional[List[:class:`str`]]
The new list of :ddocs:`OAuth2 scopes <topics/oauth2#shared-resources-oauth2-scopes>` of
the default user installation context. Can be ``None`` to remove the scopes.

.. versionadded: 2.5
user_install_permissions: Optional[:class:`Permissions`]
The new permissions of the default user installation context. Can be ``None`` to remove the permissions.

.. versionadded: 2.5
reason: Optional[:class:`str`]
The reason for editing the application. Shows up on the audit log.

Expand All @@ -325,6 +383,7 @@
ValueError
The image format passed in to ``icon`` or ``cover_image`` is invalid. This is also raised
when ``install_params_scopes`` and ``install_params_permissions`` are incompatible with each other.
or when ``guild_install_scopes`` and ``guild_install_permissions`` are incompatible with each other.

Returns
-------
Expand Down Expand Up @@ -389,6 +448,51 @@

if tags is not MISSING:
payload['tags'] = tags

integration_types_config: Dict[str, Any] = {}
if guild_install_scopes is not MISSING or guild_install_permissions is not MISSING:
guild_install_params: Optional[Dict[str, Any]] = {}
if guild_install_scopes in (None, MISSING):
guild_install_scopes = []

if "bot" not in guild_install_scopes and guild_install_permissions is not MISSING:
raise ValueError("'bot' must be in guild_install_scopes if guild_install_permissions is set")

if guild_install_permissions in (None, MISSING):
guild_install_params['permissions'] = 0
else:
guild_install_params['permissions'] = guild_install_permissions.value

guild_install_params['scopes'] = guild_install_scopes

integration_types_config['0'] = {'oauth2_install_params': guild_install_params or None}
else:
if guild_install_permissions is not MISSING:
raise ValueError("guild_install_scopes must be set if guild_install_permissions is set")

if user_install_scopes is not MISSING or user_install_permissions is not MISSING:
user_install_params: Optional[Dict[str, Any]] = {}
if user_install_scopes in (None, MISSING):
user_install_scopes = []

if "bot" not in user_install_scopes and user_install_permissions is not MISSING:
raise ValueError("'bot' must be in user_install_scopes if user_install_permissions is set")

if user_install_permissions in (None, MISSING):
user_install_params['permissions'] = 0
else:
user_install_params['permissions'] = user_install_permissions.value

user_install_params['scopes'] = user_install_scopes

integration_types_config['1'] = {'oauth2_install_params': user_install_params or None}
else:
if user_install_permissions is not MISSING:
raise ValueError("user_install_scopes must be set if user_install_permissions is set")

if integration_types_config:
payload['integration_types_config'] = integration_types_config

data = await self._state.http.edit_application_info(reason=reason, payload=payload)
return AppInfo(data=data, state=self._state)

Expand Down Expand Up @@ -520,3 +624,22 @@
def __init__(self, data: InstallParamsPayload) -> None:
self.scopes: List[str] = data.get('scopes', [])
self.permissions: Permissions = Permissions(int(data['permissions']))


class IntegrationTypeConfig:
"""Represents the default settings for the application's installation context.

.. versionadded:: 2.5

Attributes
----------
oauth2_install_params: Optional[:class:`AppInstallParams`]
The install params for this installation context's default in-app authorization link.
"""

def __init__(self, data: AppIntegrationTypeConfigPayload) -> None:
self.oauth2_install_params: Optional[AppInstallParams] = None
try:
self.oauth2_install_params = AppInstallParams(data['oauth2_install_params']) # type: ignore # EAFP

Check warning on line 643 in discord/appinfo.py

View workflow job for this annotation

GitHub Actions / check 3.x

Unnecessary "# type: ignore" comment
except KeyError:
pass
1 change: 1 addition & 0 deletions discord/http.py
Original file line number Diff line number Diff line change
Expand Up @@ -2620,6 +2620,7 @@ def edit_application_info(self, *, reason: Optional[str], payload: Any) -> Respo
'cover_image',
'interactions_endpoint_url ',
'tags',
'integration_types_config',
)

payload = {k: v for k, v in payload.items() if k in valid_keys}
Expand Down
7 changes: 6 additions & 1 deletion discord/types/appinfo.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@

from __future__ import annotations

from typing import TypedDict, List, Optional
from typing import Literal, Dict, TypedDict, List, Optional
from typing_extensions import NotRequired

from .user import User
Expand All @@ -38,6 +38,10 @@ class InstallParams(TypedDict):
permissions: str


class AppIntegrationTypeConfig(TypedDict):
oauth2_install_params: NotRequired[InstallParams]


class BaseAppInfo(TypedDict):
id: Snowflake
name: str
Expand Down Expand Up @@ -69,6 +73,7 @@ class AppInfo(BaseAppInfo):
tags: NotRequired[List[str]]
install_params: NotRequired[InstallParams]
custom_install_url: NotRequired[str]
integration_types_config: NotRequired[Dict[Literal["0", "1"], AppIntegrationTypeConfig]]


class PartialAppInfo(BaseAppInfo, total=False):
Expand Down
8 changes: 8 additions & 0 deletions docs/api.rst
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,14 @@ AppInstallParams
.. autoclass:: AppInstallParams()
:members:

IntegrationTypeConfig
~~~~~~~~~~~~~~~~~~~~~~

.. attributetable:: IntegrationTypeConfig

.. autoclass:: IntegrationTypeConfig()
:members:

Team
~~~~~

Expand Down
Loading